二叉树高度-该算法如何在python中工作?

时间:2018-09-05 23:51:59

标签: python recursion binary-tree

我碰到了这种算法,以发现二叉树的高度。有谁能够解释它是如何工作的?具体来说,我对max函数内部的递归调用感到困惑。每次迭代的最大比较值是多少?如何在不引起TypeError的情况下将输出加到1?谢谢!

def get_height(root):
if root is None: 
    return 0
return 1 + max(get_height(root.left), get_height(root.right))

2 个答案:

答案 0 :(得分:2)

  

具体来说,我对max函数内部的递归调用感到困惑。每次迭代的最大比较值是多少?如何在不引起TypeError的情况下将输出加到1?

您要调用一个函数两次,并将这两个函数调用的返回值传递给max。因此,max正在比较此函数返回的结果。

如果不清楚,让我们分解一线:

left_height = get_height(root.left)
right_height = get_height(root.right)
max_height = max(left_height, right_height)
return 1 + max_height

由于我们要调用的函数始终返回一个整数,因此max会比较两个整数,这将为您提供两个整数中较大的一个。显然,我们可以加1。

换句话说,树的高度比任何一个子树的高度高1。


您可能认为我在那儿作弊。当我不得不假设该函数来证明它时,如何证明该函数始终返回整数?

关键在于递归是归纳的。如果您不太懂数学,那是一种很好的说法:

  • 如果基本情况始终返回整数,
  • 并且递归总是调用较小的情况
  • 如果我们总是返回一个整数,只要所有较小的情况都返回一个整数
  • 然后我们总是返回一个整数。

第一部分很简单:如果为None,则返回0。

第二部分来自树的定义:树的左分支和树的右分支始终是树的较小子树。 (对于循环图,root.left可能是root或其祖父母,这不是真的。)

第三部分是答案上半部分的解释。

我们完成了。

答案 1 :(得分:2)

在代码中添加一些行将有助于弄清发生了什么。
这里是表示树的类。

class Tree:
    def __init__(self,id,left=None,right=None):
        self.id = id
        self.left = left
        self.right = right

还有一个查找高度的函数。

def get_height(root):
    if root is None: 
        return 0

    my_height = 1 + max(get_height(root.left), get_height(root.right))
    print("id :{} height: {}".format(root.id,my_height))
    return my_height

t = Tree(1,Tree(2,Tree(4),Tree(5)),Tree(3))

t如下所示。

     1
    / \
   2   3
  / \   
 4   5 

调用get_height(t)时,输出如下:

id :4 height: 1
id :5 height: 1
id :2 height: 2
id :3 height: 1
id :1 height: 3

该调用从根开始,直到到达叶节点后,该函数将使用None进行调用。
假设已经到达叶子(例如,节点4)。节点4上get_height()的结果为1 + max(get_height(None),get_height(None)) = 1 + max(0,0) =1
因此,节点4返回1。调用者(节点4的父节点,即节点2)将从1获取Node 4,并从1获取Node 5
因此,它将得出结论,其高度为1+max(1,1)=2并将该值返回给父节点。
以同样的方式,节点1(根)将从2获得Node 2,并从1获得Node 3,并将其高度计算为1+max(1,2)=3
树的高度为3,根为高度3。