私の場合はベクトルですが、この投稿の推奨事項に従って定義されたツリーがあるとします。これは問題にならないことを願っています(Programming Clojureの本のベクトルです)。
(def tree [1 [[2 [4] [5]] [3 [6]]]])
これは次のようになります。
1
/ \
2 3
/ \ |
4 5 6
ここで、キューなどの従来の手段を使用せずに、ツリーを幅優先でトラバースし、代わりにスタックのみを使用して情報を渡したいと思います。これが最も簡単なルートではないことは知っていますが、私は主に運動としてそれを行っています。また、この時点では、コレクションを返す予定はありません(後で演習として理解します)。代わりに、ノードを移動しながらノードを印刷します。
私の現在の解決策(Clojureから始めたばかりですが、いいですね):
(defn breadth-recur
[queue]
(if (empty? queue)
(println "Done!")
(let [collections (first (filter coll? queue))]
(do
; print out nodes on the current level, they will not be wrapped'
; in a [] vector and thus coll? will return false
(doseq [node queue] (if (not (coll? node)) (println node)))
(recur (reduce conj (first collections) (rest collections)))))))
最後の行は意図したとおりに機能しておらず、修正方法に困惑しています。私は自分が何を望んでいるのかを正確に知っています。ベクトルの各レイヤーをはがし、結果を連結して繰り返しに渡す必要があります。
私が見ている問題は主に:
IllegalArgumentException Don't know how to create ISeq from: java.lang.Long
基本的に、 conjはlongにベクトルを追加するのが好きではありません。conjをconcatと交換すると、連結している2つの項目のいずれかがベクトルでない場合に失敗します。conjとconcatの両方が直面すると失敗します:
[2 [4] [5] [3 [6]]]
ここでは、両方の位置のベクトルとプリミティブの両方で機能する、本当に基本的な操作が欠けているように感じます。
助言がありますか?
編集1:
ツリーは実際には次のようになります(Joostに感謝します!):
(def tree [1 [2 [4] [5]] [3 [6]]])
ただし、幅優先の解決策はまだ見つかりません。