Skip to content

Instantly share code, notes, and snippets.

@dumptruckman
Last active July 27, 2018 23:48
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save dumptruckman/f5bb47c7b6f56c40af9a2ce6097dc180 to your computer and use it in GitHub Desktop.
Save dumptruckman/f5bb47c7b6f56c40af9a2ce6097dc180 to your computer and use it in GitHub Desktop.
A0A0 interp clojure
(require '[clojure.string :as s])
(use 'clojure.zip)
(defn vectorize-program [code]
(let [t #(read-string (.substring % 1))]
(mapv #(mapv (juxt first t) (into [] (re-seq #"\w-?\d+" %)))
(s/split-lines code))))
(defn prep-code [code]
(down (vector-zip (vectorize-program code))))
(defn get-line [z n]
(loop [z z
n n]
(cond
(< n 0) (recur (left z) (inc n))
(> n 0) (recur (right z) (dec n))
:else z)))
(defn operand [z modify]
(loop [z (down z)]
(if-not (nil? z)
(if (= (-> z down node) \V)
(-> (let [arg (-> z down right)]
(edit arg (fn [arg] (modify arg)))) up up)
(recur (right z))))))
(defn perform [z]
(if (nil? (down z))
(right z)
(let [o (-> z down first)
arg (-> z down first last)
z (-> z down remove)]
(case (first o)
\A (right (get-line
(let* [line (get-line z arg)
in (down line)]
(edit line (fn [l] (apply conj l (node z)))))
(- arg)))
\C (right (get-line (edit (get-line z arg) (fn [l] [])) (- arg)))
\G (get-line z arg)
\V (right (-> (edit (-> z down down right) (fn [l] arg)) up up))
\O (right (do (print arg) z))
\P (right (do (print (char (mod arg 256))) z))
\I (right (operand z (fn [a] (if (= arg 0)
(.nextInt (java.util.Scanner. *in*))
(.read *in*)))))
\S (right (operand z #(+ % arg)))
\D (right (operand z #(- % arg)))
\M (right (operand z #(* % arg)))
\L (right (operand z #(cond (> % arg) 1 (< % arg) -1 :else 0)))
z))))
(defn interpret [code]
(loop [z (prep-code code)]
(let [x (perform z)]
(if (nil? x)
nil
(recur x)))))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment