1次元セルオートマトン

いわゆる「ルール30」。
もっとコンパクトなコードにする方法があったら教えてください。

(defn next-cell-state [x y z]
  (cond 
    (and (= x "□") (= y "□") (= z "□")) "□"
    (and (= x "□") (= y "□") (= z "■")) "■"
    (and (= x "□") (= y "■") (= z "□")) "■"
    (and (= x "□") (= y "■") (= z "■")) "■"
    (and (= x "■") (= y "□") (= z "□")) "■"
    (and (= x "■") (= y "□") (= z "■")) "□"
    (and (= x "■") (= y "■") (= z "□")) "□"
    (and (= x "■") (= y "■") (= z "■")) "□"))

(defn char-at [str index]
  (subs str index (inc index)))

(defn- next-line-state [current]
    (for [x (range 0 30)]
      (next-cell-state
        (char-at current x)
        (char-at current (inc x))
        (char-at current (inc (inc x))))))

(defn next-state [current]
  (str "■"
       (apply str (next-line-state current))
       "■"))

(defn next-state-loop [current]
  (iterate next-state current))

(def initial-state "■■□■□■□□□□□□□■□□□□□■□□□■□■□□□□□■")

(for [line (take 20 (next-state-loop initial-state))] (println line))