后序遍历实现同值子树计数:Python递归解法返回值偏少问题求助
计数偏少的核心问题
你写的后序遍历逻辑整体方向是对的,但出现计数结果小于正确值的核心原因是踩到了Python逻辑与的短路求值坑。
在处理双孩子节点的判断分支中,你直接将两个子树的递归调用写在了and连接的判断条件里:
if self.isUnivalSubtree(root.left) and self.isUnivalSubtree(root.right) and (root.val == root.left.val) and (root.val == root.right.val):
当左子树的isUnivalSubtree返回False时,后续的isUnivalSubtree(root.right)会因为逻辑短路完全不被执行。而这个递归调用本身承担了右子树内部所有同值子树的计数累加逻辑,一旦触发短路跳过调用,右子树中所有合法的同值子树都会被漏统计。
举个会触发这个bug的典型测试用例:
2 / \ 2 2 / 3
原代码的执行流程:
- 根节点进入双孩子分支,优先调用左子树的递归:遍历到叶子节点3,累加计数为1,最终左子树因节点值不匹配返回
False - 由于
and的短路特性,右孩子2的递归完全不会被触发,这个叶子节点本应累加的计数直接丢失 - 最终代码返回计数1,但正确答案应为2(叶子3、右叶子2)
修复方案
你不需要根据左右孩子的存在情况写多段重复的判断逻辑,统一处理所有分支即可,同时从根本上避免逻辑短路漏调用子树递归的问题:
- 对任意节点,先无条件完成左右子树的同值判断,将返回结果分别存入临时变量,确保所有子树的计数逻辑一定会被执行
- 初始标记当前节点所在子树为同值,只要出现“某侧子树不是同值”、“当前节点值与存在的孩子值不相等”的情况,就将同值标记置为
False - 最终如果同值标记为
True,说明当前节点构成合法的同值子树,执行计数累加
修复后的参考实现:
class Solution: def countUnivalSubtrees(self, root: TreeNode) -> int: if not root: return 0 self.count = 0 self.check_unival(root) return self.count def check_unival(self, root: TreeNode) -> bool: # 叶子节点天然是同值子树 if not root.left and not root.right: self.count += 1 return True is_current_unival = True # 递归左子树,不受后续判断逻辑影响 if root.left: left_valid = self.check_unival(root.left) if not left_valid or root.val != root.left.val: is_current_unival = False # 递归右子树,不受后续判断逻辑影响 if root.right: right_valid = self.check_unival(root.right) if not right_valid or root.val != root.right.val: is_current_unival = False # 当前节点构成同值子树则累加计数 if is_current_unival: self.count += 1 return is_current_unival
逻辑说明
- 同值子树的判定规则是:以当前节点为根的整棵子树中,所有节点的值完全相等,叶子节点天然满足这个规则
- 采用后序遍历的思路完全符合这类问题的求解逻辑:必须等左右子树的判定结果全部返回后,才能结合当前节点的值,判断当前节点所在的子树是否为同值结构
内容的提问来源于stack exchange,提问作者Lynette
相关产品推荐
相关产品推荐

