问题概述
给定两个二叉树的根节点 p 和 q,编写一个函数来检验这两棵树是否相同。
如果两个树在结构上相同,并且节点具有相同的值,则认为它们是相同的。
解法 1:迭代(使用队列)
工作原理
使用队列逐层比较节点(BFS 方法):
python
class Solution:
def isSameTree(self, p, q):
queue = [(p, q)]
while queue:
node1, node2 = queue.pop(0)
if not node1 and not node2:
continue
if not node1 or not node2:
return False
if node1.val != node2.val:
return False
queue.append((node1.left, node2.left))
queue.append((node1.right, node2.right))
return True
复杂度分析
- 时间复杂度 : O(n²) -
queue.pop(0)在 Python 列表中是 O(n) 操作 - 空间复杂度: O(n) - 队列在最坏情况下可以容纳 n/2 个节点(完全树)
何时使用
- 递归的替代方案
- 避免非常深的树的潜在栈溢出
- 需要逐层比较时有用
解法 2:递归(推荐)
工作原理
递归地比较两个树中对应的节点:
python
class Solution:
def isSameTree(self, p, q):
if not p and not q:
return True
if not p or not q:
return False
if p.val != q.val:
return False
return (self.isSameTree(p.left, q.left) and
self.isSameTree(p.right, q.right))
复杂度分析
- 时间复杂度: O(n) - 每个节点恰好访问一次
- 空间复杂度: O(h) - 递归栈深度等于树的高度(最坏情况 O(n) 对于倾斜树)
何时使用
- 推荐 - 最直观和简洁的解决方案
- 自然的递归结构匹配树结构
- 易于理解和实现
对比
| 方法 | 时间 | 空间 | 最佳适用 |
|---|---|---|---|
| 迭代(列表) | O(n²) | O(n) | 不推荐 - 由于 pop(0) 较慢 |
| 递归 | O(n) | O(h) | 大多数情况,直观,最快 |
总结
递归解决方案通常更受欢迎,因为:
- 更快 - 实际性能更好(O(n) vs O(n²))
- 更简单 - 更直观,易于理解
- 自然匹配 - 递归完美匹配树结构
关键洞察是在每个节点检查三个条件:两者都是 None(相同)、一个是 None(不同)或值匹配(继续递归)。