NB. Definitions for Computability Chapter

tape =: 1 ; 1 ; 1 ; 1 ; 0 ; 0

even_or_odd =: ((0 ; 1 ; 1 ; 1 ; 'r') ; (0 ; 0 ; 2 ; 0 ; 'r') ; (1 ; 1 ; 0 ; 1 ; 'r') ; (1 ; 0 ; 3 ; 0 ; 'r') ; (2 ; 0 ; 'halt' ; 'even' ; 'l') ; (2 ; 1 ; 'halt' ; 'even' ; 'l') ; (3 ; 0 ; 'halt' ; 'odd' ; 'l') ; < (3 ; 1 ; 'halt' ; 'odd' ; 'l'))

read_symbol =: monad define script
('tape' ; 'position') =. y.
if. (position < 0) or (position >: tally tape)
  do. error 'invalid tape position' , format position
  else. open position from tape
end.
)

lookup_state_symbol =: monad define script
('state' ; 'symbol' ; 'machine') =. y.
if. nullp machine
    do. error 'symbol, ' , (format symbol) , ' or state, ' , (format state) , ' not found'
  elseif. (state match head head machine) and symbol match head rest head machine
    do. head machine
  elseif. 1
    do. lookup_state_symbol state ; symbol ; box rest machine
end.
)

write_new_symbol =: monad define script
('tape' ; 'position' ; 'new_symbol') =. y.
(box new_symbol) position amend tape
)

new_position =: monad define script
('i' ; 'move') =. y.
if. 'l' match move
    do. i - 1
  elseif. 'r' match move
    do. i + 1
  elseif. 1
    do. error 'invalid move ' , format move
end.
)

turing =: monad define script
('machine' ; 'state' ; 'tape' ; 'position') =. y.
if. 'halt' match state
  do. 'halt, position=' , (format position) , 'tape=' , format  tape
  else. symbol =. read_symbol tape ; position
        five_tuple =. lookup_state_symbol state ; symbol ; box machine
    turing machine ; (> 2 from five_tuple) ; (write_new_symbol tape ; position ; > 3 from five_tuple) ; new_position position ; 4 from five_tuple
end.
)

traced_turing =: monad define script
('machine' ; 'state' ; 'tape' ; 'position') =. y.
entering state ; tape ; position
if. 'halt' match state
  do. 'halt, position=' , (format position) , 'tape=' , format  tape
  else. symbol =. read_symbol tape ; position
        five_tuple =. lookup_state_symbol state ; symbol ; box machine
    traced_turing machine ; (> 2 from five_tuple) ; (write_new_symbol tape ; position ; > 3 from five_tuple) ; new_position position ; 4 from five_tuple
end.
)

mystery =: monad define script
if. 0 = 2 residue y.
  do. y. =. y. % 2
    if. y. > 1
      do. y. , mystery y.
      else. 1
    end.
  else. y. =. 1 + 3 * y.
    if. y. > 1
      do. y. , mystery y.
      else. 1
    end.
end.
)
