我正在尝试编写一个输入特定深度二叉树的方案程序。例如,二叉树的根是1,然后左子树的根是2,依此类推。我应该让它输出树中有深度的数据表达式。现在我有下面的代码,但我不断收到错误消息:
Error in null?: expected a list; got '1'.
如果您可以使用我正在使用的代码中的相同术语来解释这一点,那么在我学习时会很棒,而且我不知道如何使用一些更大的表达式。
这是代码
(define fetch-exp
(λ (n bt)
(cond [(empty-tree? bt) ▽#f]
[(> n (tree-depth (left-tree bt))) ▽#f]
[(> n (tree-depth (right-tree bt))) ▽#f]
[(one? n) (root bt)]
[(> (tree-depth (left-tree bt)) (tree-depth (right-tree bt)))
(fetch-exp (left-tree bt) (sub1 n))]
[(> (tree-depth (right-tree bt)) (tree-depth (left-tree bt)))
(fetch-exp (right-tree bt) (sub1 n))]
[else ▽#f])))
答案 0 :(得分:2)
您的主要问题是您对fetch-exp
的递归调用交换了参数的顺序。它应该是(fetch-exp (sub1 n) (left-tree bt))
和(fetch-exp (sub1 n) (right-tree bt))
。或者,更改函数的参数顺序:(lambda (bt n) ...)
。
答案 1 :(得分:2)
计算每个孩子的深度将永远需要,因为它本身就是一个树遍历。此外,你可能会为每一方做两次。如果必须这样做,最好将结果绑定在let语句中。 (或者您进行案例分析的任何地方,并且不止一次地使用潜在昂贵评估的结果)。否则修改程序,使其仅评估一次。
(define (fetch-exp n bt)
(cond ((empty-tree? bt) #f)
((= 1 n) (root bt))
(else (or (fetch-exp (sub1 n) (left-tree bt))
(fetch-exp (sub1 n) (right-tree bt))))))
这和你的一样只会沿着左边的树枝走下去。如果失败,堆栈上的or语句将继续尝试,直到找到合适的数据项或到达树的最右下方分支。在最糟糕的情况下,你最终遍历树一次,这实际上是非空树中进程的最佳情况,因为你甚至在检查n是否为1之前就行走了树。