文 | 景禹
来源:图解面试算法「ID: LeetCodeAnimation」
题目来源于 LeetCode 上第 617 号问题:合并二叉树。题目难度为 Easy,目前通过率为 75.9% 。
题目描述
给定两个二叉树,想象当你将它们中的一个覆盖到另一个上时,两个二叉树的一些节点便会重叠。
你需要将他们合并为一个新的二叉树。合并的规则是如果两个节点重叠,那么将他们的值相加作为节点合并后的新值,否则不为 NULL 的节点将直接作为新二叉树的节点。
”
输入:
Tree 1 Tree 2
1 2
/ \ / \
3 2 1 3
/ \ \
5 4 7
输出:
合并后的树:
3
/ \
4 5
/ \ \
5 4 7
题目解析
这道题目主要考察二叉树的遍历方式,前序遍历、中序遍历和后序遍历、层序遍历,原则上可以采用任何一种遍历方式解决此题。本文题解我们以前序遍历方式进行讲解。
解法一:递归
采用递归的方式很简单,我们只需要将前序遍历的代码稍加修改即可。
递归动画理解
代码实现
public class Solution {
public TreeNode mergeTrees(TreeNode t1, TreeNode t2) {
if (t1 == null)
return t2;
if (t2 == null)
return t1;
t1.val += t2.val; //中,可以对这行代码进行位置调整,实现中序和后序遍历
t1.left = mergeTrees(t1.left, t2.left); //左
t1.right = mergeTrees(t1.right, t2.right); //右
return t1;
}
}
解法二:迭代
对于二叉树的前序遍历,我们可以采用栈数据结构实现递归的迭代版本,对于这道题目也是同样的道理,唯一需要注意的是每一次出栈和入栈的元素是两颗待合并二叉树相同位置的两个元素。
迭代动画理解:
代码实现:
public class Solution {
public TreeNode mergeTrees(TreeNode t1, TreeNode t2) {
if (t1 == null)
return t2;
Stack < TreeNode[] > stack = new Stack < > ();
stack.push(new TreeNode[] {t1, t2});
while (!stack.isEmpty()) {
TreeNode[] t = stack.pop();
if (t[0] == null || t[1] == null) {
continue;
}
t[0].val += t[1].val;
//与二叉树的先序遍历类似,一定要注意压栈顺序,先右子结点
if (t[0].right == null) {
t[0].right = t[1].right;
} else {
stack.push(new TreeNode[] {t[0].right, t[1].right});
}
//后左子节点。
if (t[0].left == null) {
t[0].left = t[1].left;
} else {
stack.push(new TreeNode[] {t[0].left, t[1].left});
}
}
return t1;
}
}
复杂度分析
时间复杂度:O(N)。
空间复杂度:O(N)。
老规矩,兄弟们还记得么,右下角的 “在看” 点一下,如果感觉文章内容不错的话,记得分享朋友圈让更多的人知道!
每晚 8 点,不见不散,一起刷 LeetCode !