检查二叉树是否对称的技术

时间:2019-06-22 18:26:51

标签: python c++ algorithm data-structures binary-tree

给出一棵二叉树,检查它是否是其自身的镜像(即,围绕其中心对称)。 问题链接为here

recursion method需要遍历树两次。

但是其中一条评论提供了一种解决方案,即使用一种称为“空检查”的技术。我不明白为什么这样才能避免两次检查树?

这是他的C ++代码:

bool isSymmetric(TreeNode* root) {
        if (!root) return true;
        return isSymmetric(root->left, root->right);
    }

    bool isSymmetric(TreeNode* t1, TreeNode* t2){
        if (!t1 && !t2) return true;
        if (!t1 || !t2) return false;
        return t1->val == t2->val
            && isSymmetric(t1->left, t2->right)
            && isSymmetric(t1->right, t2->left);
    }

我也试图将其修改为python3,我的代码也通过了所有测试用例!

这是我的代码:

# Definition for a binary tree node.
# class TreeNode:
#     def __init__(self, x):
#         self.val = x
#         self.left = None
#         self.right = None
class Solution:
    def isSymmetric(self, root):
        return self.helper(root)
    def helper(self,root):
        if root is None:
            return True

        #why we can redefine the helper here?
        def helper(left,right):
            if left is None and right is None:
                return True
            if left is None or right is None:
                return False
            return left.val==right.val and helper(left.left,right.right) and helper(left.right,right.left)

        return helper(root.left,root.right)

我以前从未遇到过这种递归。

(1)为什么我们可以在helper函数本身中用不同的参数重新定义函数helper?

(2)我的直觉告诉我,辅助函数返回到根后将停止执行,因此不会对树进行两次检查。但是我不知道为什么。

2 个答案:

答案 0 :(得分:2)

def语句实际上只是一个花哨的赋值语句。在Solution.helper中,您将定义一个名为helper的本地变量,该变量绑定到另一个函数。结果,Solution.helper内部的所有引用以及名称为helper的本地函数都将解析为本地函数。

Solution.helper不是递归函数;只有本地功能。您可以写出与

相同的内容(不那么令人困惑,但等效)
class Solution:
    def isSymmetric(self, root):
        return self.helper(root)
    def helper(self,root):
        if root is None:
            return True

        def helper2(left,right):
            if left is None and right is None:
                return True
            if left is None or right is None:
                return False
            return left.val==right.val and helper2(left.left,right.right) and helper2(left.right,right.left)

        return helper2(root.left,root.right)

答案 1 :(得分:0)

函数isSymmetric(TreeNode* root的作用非常简单。首先,如果树为空,则返回true,如果树不是空的,它将检查其左子节点是否是其右子节点的镜像,这在isSymmetric(TreeNode* t1, TreeNode* t2)中发生。因此,让我们尝试了解第二个函数的工作原理。它本质上被设计为采用两棵树并检查它们是否互为镜像。怎么样?首先,它会进行明显的检查。如果一个是null,另一个不是false,如果两个都是null,则返回true。有趣的是,当两者都是潜在的树时。只要一个孩子的左孩子是另一个孩子的右孩子的镜子,反之亦然。您可以画一棵树,看看为什么会这样。模式应该是不言自明的。