如何递归计算Clojure中树结构的深度?

时间:2016-04-26 10:53:37

标签: recursion clojure tree

所以我对Clojure有一个非常基本的理解,并且想要计算使用包含向量本身的向量定义的树的深度。例如,[1 [2] [3 [4]]]将代表一棵树,其中1是根,而[2]是1的孩子,[3 [4]]是子树。

(defn height[tree]
(if(empty? tree)
    (1); Base case
    (inc (apply max (map  height (next tree))))); Calculate the height for every subtree and return maximum
)

我在想这个方法会起作用,因为它应该递归地计算每个子树的深度以返回最大值。但是,当我尝试运行此方法时,我得到一个非法参数异常。

2 个答案:

答案 0 :(得分:4)

带拉链的尾递归变体:

(require '[clojure.zip :as z])

(defn height-2 [tree]
  (loop [curr (z/zipper coll? seq nil tree) h 0]
    (if (z/end? curr) h
        (recur (z/next curr)
               (if (z/branch? curr) h
                   (-> curr z/path count (max h)))))))

在repl中:

user> (height-2 [1 [2] [3 [4] ]])
3
user> (height-2 (nth (iterate (partial vector 1) []) 1000))
1000
user> (height-2 (nth (iterate (partial vector 1) []) 100000))
100000

答案 1 :(得分:3)

  • (1)错了。它尝试将1作为函数执行。
  • 你需要能够应对树中的叶子,而不是 载体
  • next来电错误 - 请将其删除。

尝试

(defn height [tree]
  (if (vector? tree)
   (if (empty? tree)
     1
     (inc (apply max (map height tree))))
    0))

例如,

(height [1 [2] [3 [4] ]]) ; 3

稍微简单的版本是

(defn height [tree]
  (if (vector? tree)
    (inc (apply max 0 (map height tree)))
    0))

通过向0提供初始/默认参数max,我们处理没有条件的空集合。