Leetcode Hot 100 继续推进,这一题轮到二叉树里的“照镜子选手”:对称二叉树。
它问得很直白:
给你一棵二叉树,判断它是不是轴对称。
翻成人话就是:
- 左边看过去
- 和右边照镜子看回来
- 得长得一模一样
这题不靠花活,核心就是四个字:镜像比较。
题目链接
题目描述
给你一个二叉树的根节点 root,检查它是否轴对称。

解题思路:递归判断两棵树是否互为镜像
这题表面是在问“一棵树是否对称”, 其实更适合改写成另一个问题:
左子树和右子树,是否互为镜像?
只要这个问题成立,整棵树就是对称的。
于是我们定义一个递归函数:
dfs(q, p)表示判断节点 q 和节点 p 这两棵子树,是否互为镜像。
镜像比较的规则
想判断两棵树是不是镜像,得同时满足下面几条:
1. 两个节点都为空
那当然对称。
2. 一个为空,一个不为空
那肯定不对称。
3. 两个节点值不同
也不对称。
4. 两个节点值相同,还要继续比较它们的孩子
注意这里不是“左对左、右对右”, 而是镜像关系,所以要交叉比较:
q.left和p.rightq.right和p.left
也就是说:
外侧对外侧,内侧对内侧。
这才是真正的镜子逻辑。
代码实现
class Solution(object): def isSymmetric(self, root): """ :type root: Optional[TreeNode] :rtype: bool """ def dfs(q, p): if q is None or p is None: return p is q if q.val != p.val: return False return dfs(q.right, p.left) and dfs(q.left, p.right)
if root is None: return True return dfs(root.left, root.right)代码解析
1. 空节点怎么处理
if q is None or p is None: return p is q这句写得很精炼。
它表示:
- 如果
q和p中有一个为空 - 那么只有在 两个都为空 的情况下才返回
True
换句话说:
None对None,算对称None对 非空节点,直接淘汰
2. 节点值不同,立刻返回 False
if q.val != p.val: return False镜像不只是结构要对,数值也得对上。
如果当前这两个节点值都不一样, 那后面孩子再努力也救不回来,直接结束。
3. 递归比较左右子树的镜像位置
return dfs(q.right, p.left) and dfs(q.left, p.right)这是整题的灵魂。
很多人第一次写这题,容易顺手写成:
dfs(q.left, p.left) and dfs(q.right, p.right)但那样比较的是“是否相同”, 不是“是否镜像”。
镜像必须交叉着看:
- 左树的左边,要对右树的右边
- 左树的右边,要对右树的左边
代码里写成哪个在前其实都行, 关键是这两个配对必须交叉。
4. 为什么从 root.left 和 root.right 开始
return dfs(root.left, root.right)因为整棵树是否对称, 本质就是看根节点的左右两棵子树是不是互为镜像。
如果根节点本身就是空树:
if root is None: return True空树也算对称,这个别漏。
示例理解
比如这棵树:
1 / \ 2 2 / \ / \3 4 4 3它是对称的。
因为:
- 左边的
2对右边的2 - 左边的
3对右边的3 - 左边的
4对右边的4
而且位置也完全是镜像关系。
但如果是下面这样:
1 / \ 2 2 \ \ 3 3它就不是对称的。
虽然两边都有 3,
但位置不对:
- 左边的
3在右孩子位置 - 右边的
3也在右孩子位置
这不是镜像,是“同向站队”,所以不行。
复杂度分析
时间复杂度
每个节点最多访问一次,所以时间复杂度是:
O(n)其中 n 是二叉树节点总数。
空间复杂度
递归调用会使用系统栈,空间复杂度取决于树高:
O(h)其中 h 是二叉树高度。
- 平衡树情况下约为
O(log n) - 极端退化成链表时,最坏为
O(n)
易错点总结
1. 把镜像比较写成了相同结构比较
错法很常见:
dfs(q.left, p.left) and dfs(q.right, p.right)这不是镜像比较,这是“同步对账”。
真正要写的是:
dfs(q.left, p.right) and dfs(q.right, p.left)2. 空节点判断没写全
如果只判断:
if q is None and p is None: return True那还不够。
因为还要处理“一个空、一个不空”的情况。
你现在这句:
if q is None or p is None: return p is q写法很利索,属于短小精悍型。
3. 忘记处理空树
if root is None: return True空树也是对称树,别让它在门口被错杀。
小结
这题的核心其实就一句:
判断一棵树是否对称,就是判断它的左子树和右子树是否互为镜像。
而镜像判断的关键,就是交叉递归比较:
- 左对右
- 右对左
写熟之后,这类“二叉树结构比较题”会顺很多。
这题不难,但很经典,属于面试里那种看着温柔、其实专查你递归基本功的题。 镜子一摆,左右一比,代码要稳,手别抖。🦐