给定两个二叉树,想象当你将它们中的一个覆盖到另一个上时,两个二叉树的一些节点便会重叠。你需要将他们合并为一个新的二叉树。合并的规则是如果两个节点重叠,那么将他们的值相加作为节点合并后的新值,否则不为 NULL 的节点将直接作为新二叉树的节点。
该题的解题思路可以分为以下几个关键部分:递归思想、合并条件、节点复用。
1. 递归思想
在本题中,递归用于合并两棵树的每个节点。如果两棵树的当前节点都存在,则将它们的值相加,并递归合并它们的左子树和右子树。如果其中一个节点不存在,则返回另一个节点。
2. 合并条件
在二叉树合并的过程中,需要考虑以下几种情况:
-
其中一个树的节点为
None
:- 如果
root1
是None
,则返回root2
。 - 如果
root2
是None
,则返回root1
。
- 如果
-
两棵树的节点都存在:
- 将两个节点的值相加,作为合并后节点的值。
- 递归合并它们的左子树和右子树。
3.节点复用
在这个算法中,我们重复使用了原有的树节点,而不是创建新的树节点。这种做法的好处是:
- 节省空间:不需要额外的内存来创建新树。
- 提高效率:通过直接修改原有的树,避免了不必要的节点复制和内存分配。
因此,函数返回的 root1
就是合并后的树的根节点。
完整代码如下:
# Definition for a binary tree node.
# class TreeNode:
# def __init__(self, val=0, left=None, right=None):
# self.val = val
# self.left = left
# self.right = right
class Solution:
def mergeTrees(self, root1: TreeNode, root2: TreeNode) -> TreeNode:
# 递归终止条件:
# 但凡有一个节点为空, 就立刻返回另外一个. 如果另外一个也为None就直接返回None.
if not root1:
return root2
if not root2:
return root1
# 上面的递归终止条件保证了代码执行到这里root1, root2都非空.
root1.val += root2.val # 中
root1.left = self.mergeTrees(root1.left, root2.left) #左
root1.right = self.mergeTrees(root1.right, root2.right) # 右
return root1 # ⚠️ 注意: 本题我们重复使用了题目给出的节点而不是创建新节点. 节省时间, 空间.
首先确定递归终止条件,如果 root1
是 None
,就返回 root2
;如果 root2
是 None
,就返回 root1
。这意味着如果其中一棵树在某个节点处没有左子树或右子树,那么合并结果就是另一棵树在同一位置的子树。
合并当前节点的值,root1
和 root2
都不为空,函数将 root2
的值加到 root1
上。这是合并树的核心逻辑,表示将两个节点的值合并到一起。
root1.left = self.mergeTrees(root1.left, root2.left)
root1.right = self.mergeTrees(root1.right, root2.right)
这两行代码是对左子树和右子树进行递归调用。首先合并 root1.left
和 root2.left
,将结果赋值给 root1.left
;然后合并 root1.right
和 root2.right
,将结果赋值给 root1.right
。这实现了树的逐层合并。
最后,函数返回 root1
,即合并后的树的根节点。注意,这里没有创建新的节点,而是直接在 root1
上进行修改,这样可以节省时间和空间。