Offer 驾到,掘友接招!我正在参与2022春招系列活动-刷题打卡任务,点击查看活动详情。
题目描述
你需要采用前序遍历的方式,将一个二叉树转换成一个由括号和整数组成的字符串。 空节点则用一对空括号 "()" 表示。而且你需要省略所有不影响字符串与原始二叉树之间的一对一映射关系的空括号对。
示例 1:
输入:二叉树: [1,2,3,4]
输出:"1(2(4))(3)"
解释:
原本将是“1(2(4)())(3())”,在你省略所有不必要的空括号对之后,它将是“1(2(4))(3)”。
示例 2:
输入:二叉树: [1,2,3,null,4]
输出:"1(2()(4))(3)"
解释:
和第一个示例相似,除了我们不能省略第一个对括号来中断输入和输出之间的一对一映射关系。
思路
先理解题意,对于上面的示例1,我们先画出二叉树的图
对于根节点1,有左右2个子节点2和3,所以可以表示成"1(2)(3)"。因为2还有4这个左子节点,3没有任何子节点,所以进一步表示为"1(2(4)())(3()())"。需要省略不必要的空括号对,所以上述的结果简化为"1(2(4))(3)"。
有了上面这个模拟的过程,我们不难发现可以使用递归的方法不断向下,先表示出第0层(只有根节点),再向下表示第1层、第2层、第n层,直到整棵树的节点都表示了。对于每一个节点,它的子节点可能有这4种情况:
- 无子节点 此时假设根节点为1,那么表示的结果就是"1"
- 仅有左子节点 此时假设根节点为1,左子节点为2,那么表示的结果就是"1(2)"
- 仅有右子节点 此时假设根节点为1,右子节点为3,那么表示的结果就是"1()(3)"。注意此时表示左子节点的"()"不能省略,否则会引发歧义,认为后面的"(3)"表示的是右子节点。
- 左右均有子节点 此时假设根节点为1,左子节点为2,右子节点为3,那么表示的结果就是"1(2)(3)"。
Java版本代码
class Solution {
public String tree2str(TreeNode root) {
if (root == null) {
return "";
}
TreeNode left = root.left;
TreeNode right = root.right;
StringBuilder ans = new StringBuilder();
ans.append(root.val);
if (left == null && right == null) {
return ans.toString();
}
if (left != null && right == null) {
ans.append("(").append(tree2str(left)).append(")");
} else if (left == null && right != null) {
ans.append("()(").append(tree2str(right)).append(")");
} else {
ans.append("(").append(tree2str(left)).append(")(").append(tree2str(right)).append(")");
}
return ans.toString();
}
}