Jump to content

Execute Brain****/Common Lisp: Difference between revisions

The obvious: use local macros to create shorthand references to the slots of the state structure.
(The obvious: use local macros to create shorthand references to the slots of the state structure.)
Line 8:
(memory (make-array 1 :initial-element 0 :adjustable t))
(memory-pointer 0))
 
(defmacro with-bf-slots ((program-sym program-counter-sym
memory-sym (bf-state-memory-pointer state))-sym)
stream))obj-expr &body body)
"Macro to replace cumbersome structure slot references with
local lexical macros resembling local variables."
`(symbol-macrolet ((,program-sym (bf-state-program ,obj-expr))
(incf,program-counter-sym (bf-state-program-counter state))),obj-expr))
(setf,memory-sym (bf-state-memory state,obj-expr))
(setf (subseq,memory-pointer-sym (bf-state-memory-pointer state,obj-expr)) extent)
,@body))
 
(defun adjust-memory (state)
Line 15 ⟶ 26:
contents are shifted forward and the memory-pointer is incremented,
by an amount to make the memory ."
(condwith-bf-slots ((>=program (bf-state-memory-pointerpc mem ptr) state)
(cond ((>= ptr (length (bf-state-memory state)mem))
(adjust-array mem (bf-state1+ ptr) :initial-memoryelement state0))
(1+ (bf-state-memory-pointerminusp state)ptr)
(let ((extent :initial(-element 0ptr)))
((minusp (bf-state-memory-pointerincf ptr state)extent)
(let ((extent (old-memory (bf-state-memorycopy-pointerseq state)mem)))
(incfsetf mem (bfmake-statearray (+ (length old-memory-pointer state) extent)))
(let ((old-memorysetf (copy-seqsubseq mem (bf-stateextent) old-memory state)))))))
(setf (bf-state-memory state)
(make-array (+ (length old-memory) extent)))
(setf (subseq (bf-state-memory state) extent)
old-memory))))))
 
(defun matching-bracket-for (program bracket-index)
(loop with depth := 0
Line 40 ⟶ 47:
until (zerop depth)
finally (return index)))
 
(defun brainfuck-eval (state &optional (stream *standard-output*))
(let ((programplaces (bf-state-program statenil))
(with-bf-slots (program pc mem ptr) state
(places nil))
(loop while (< (bf-state-program-counter state)pc (length program)) do
(case (elt program (bf-state-program-counter state)pc)
(#\+ (incf (eltaref (bf-state-memory state) (bf-state-memory-pointermem state)ptr)))
(#\- (decf (eltaref (bf-state-memory state) (bf-state-memory-pointermem state)ptr)))
(#\> (incf (bf-state-memory-pointer state)ptr) (adjust-memory state))
(#\< (decf (bf-state-memory-pointer state)ptr) (adjust-memory state))
(#\[ (if (/= 0 (eltaref (bf-state-memory state) (bf-state-memory-pointermem state)ptr))
(push (1- (bf-state-program-counter state)pc) places)
(setf pc (bfmatching-statebracket-for program-counter statepc))))
(#\] (matching-bracket-forsetf programpc (bf-state-program-counterpop state))places)))
(#\]. (setfwrite-char (bfcode-state-program-counter state)char (poparef mem ptr)) placesstream)))
(placesincf nilpc)))))
(#\. (write-char (code-char (elt (bf-state-memory state)
(bf-state-memory-pointer state)))
stream)))
(incf (bf-state-program-counter state)))))
(defun bf (program) (brainfuck-eval (make-bf-state :program program)))
 
(defun bf-repl ()
(loop do (fresh-line)
Anonymous user
Cookies help us deliver our services. By using our services, you agree to our use of cookies.