在预订中遍历树

时间:2014-10-12 20:12:21

标签: clojure functional-programming

我不熟悉clojure以及函数式编程。我试图使用以下方式遍历预定的树:

(def preordercoll [])

(deftrace preorder [mytree]
  (if-not (empty? mytree)
    (do (println "position"(value mytree))
        (cons (value mytree) (preorder (left-child mytree)))
        (cons (value mytree) (preorder (right-child mytree))))
      )preordercoll) )

(preorder [45[65 [90 nil nil] [81 nil nil]] [72[82 nil nil][96 nil nil]]])

我无法在某些列表中追加节点的值,就像我尝试使用' conj'对全局变量preordercoll进行操作,但是它并不像面向对象那样工作,所以我尝试使用cons,但只返回少量值,这也是不正确的顺序。任何人都可以指导我犯了什么错误吗?

我还想过使用Partial函数但是找不到如何以递归方式提供节点的值。我不是要求代码,但请在正确的方向上绘制我以获得预订的值集合。

1 个答案:

答案 0 :(得分:1)

你正走在正确的轨道上,只需将cons电话的嵌套稍微关闭一下。首先是关于评估clojure形式的说明。其中一个关键的想法是每个表单评估的内容*这就是为什么没有" return"语言中的陈述,因为你可以说一切都是一个返回陈述,所以具有它的重点是什么。在do表达式的情况下,表达式的返回值是最后一个语句,所以:

(do 1 2 3)

返回(评估为)3。在代码中的do表达式中,它返回第二个缺点的结果,并且第一个缺点没有效果。

(do (println "position"(value mytree))
    (cons (value mytree) (preorder (left-child mytree))) ;; <-- this does nothing
    (cons (value mytree) (preorder (right-child mytree))))

相反,它听起来像你想要一个表达式,它以在左侧树上调用preorder的结果开始,然后在右侧树上结束调用preorder的结果,然后将当前节点的值附加到前面那个。

(let [left-side (preorder (left-child mytree))
      right-side (preorder (left-child mytree))
      this-value (value mytree)]
   (do (println "position" this-value)
       (cons this-value (concat right-side left-side))

*(对于学生来说)&#34;除了忽略读者maco#_&#34;