【问题标题】:Python: Recursion: Find number of leaves of binary treePython:递归:查找二叉树的叶子数
【发布时间】:2016-01-24 10:18:25
【问题描述】:

我正在尝试编写一个函数,通过合并我的 BinaryTree 类来计算二叉树的叶子数:

这是我的二叉树类:

class BinaryTree:

def __init__(self, data):
    self.data = data
    self.left = None
    self.right = None

def insert_left(self, new_data):
    if self.left == None:
        self.left = BinaryTree(new_data)
    else:
        t = BinaryTree(new_data)
        t.left = self.left
        self.left = t

def insert_right(self, new_data):
    if self.right == None:
        self.right = BinaryTree(new_data)
    else:
        t = BinaryTree(new_data)
        t.right = self.right
        self.right = t

def get_left(self):
    return self.left

def get_right(self):
    return self.right

def set_data(self, data):
    self.data = data

def get_data(self):
    return self.data

这是我编写的函数:目前它没有输出正确的值。我认为我的递归有问题,但我无法弄清楚:

def num_leaves(my_tree):
    count = 0
    if my_tree.get_left() and my_tree.get_right() is None:
        count += 1
    if my_tree.get_left():
        num_leaves(my_tree.get_left())
    if my_tree.get_right():
        num_leaves(my_tree.get_right())

    return count

输入和输出的示例是:

a = BinaryTree(1)
a.insert_left(2)
a.insert_right(3)
print(num_leaves(a))

输出:

0 

而不是 2。

我的函数背后的想法是它递归直到找到左右子树都为None的节点,然后将其加一计数。这样它就找到了每一片叶子。

我做错了什么?

【问题讨论】:

  • 您需要学习如何使用调试器。使用它,您可以逐步检查num_leaves() 的代码并检查count 的值,以找出它与您的预期不同的地方。使用它,您的问题将变得微不足道。

标签: python recursion binary-tree


【解决方案1】:

您误解了递归调用的独立性。 num_leaves 不能返回除 0 或 1 以外的任何值(如您所写)。 num_leaves 的每个实例都有自己的 count 本地副本。不要尝试将其作为运行总和,而是让 num_leaves 返回该点处或以下的叶子数。

另外,您在 num_leaves 的第一个 if 语句中误用了布尔表达式。您没有明确检查左树是否为无。尽管您所写的内容恰好以相同的方式起作用,但在我看来,您似乎没有意识到自己在做什么。

def num_leaves(my_tree):
    if my_tree is None:
        return 0
    else:
        return num_leaves(my_tree.get_left()) +
               num_leaves(my_tree.get_right())

【讨论】:

  • 可能只有 left & right 之一是子树。另一个是None。您的代码无法处理这种情况。
【解决方案2】:

乍一看,num_leaves 的代码应该是这样的:

def num_leaves(my_tree):
    count = 0
    if my_tree.get_left() is None and my_tree.get_right() is None:
        count += 1
    if my_tree.get_left():
        count += num_leaves(my_tree.get_left()) # added count +=
    if my_tree.get_right():
        count += num_leaves(my_tree.get_right()) # added count +=

    return count

我将发布一些对您的树代码的更多改进。 您实现它的方式 BinaryTree 只是一个二叉树而不是二叉搜索树。因此,我想如果您对上面的代码进行我建议的简单更改,它应该可以正常工作。

测试:

正如预期的那样,这给出了 3:

a = BinaryTree(1)
a.insert_left(2)
a.insert_right(3)
a.insert_right(4)
a.get_right().insert_left(5)
print(num_leaves(a))

正如预期的那样,这给出了 2:

a = BinaryTree(1)
a.insert_left(2)
a.insert_right(3)
print(num_leaves(a))

正如预期的那样,这给出了 2:

a = BinaryTree(1)
a.insert_left(2)
a.insert_right(3)
a.get_right().insert_left(5)
print(num_leaves(a))

【讨论】:

    【解决方案3】:

    我建议将所有与 btree 相关的函数保留在类中。那是面向对象的。

    class BinaryTree:
        ... your code ...
    
        def is_leaf(self):
            return self.right is None and self.left is None
    
        def count_leaves(self):
            if self.is_leaf():
                return 1
            count = 0
            if self.right is not None:
                count += self.right.count_leaves()
            if self.left is not None:
                count += self.left.count_leaves()
            return count
    

    【讨论】:

      猜你喜欢
      • 2016-01-17
      • 2016-07-24
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-09-15
      • 1970-01-01
      • 2015-06-05
      相关资源
      最近更新 更多