606. 根据二叉树创建字符串题解
题目来源:606. 根据二叉树创建字符串
2022.03.19 每日一题
LeetCode 题解持续更新中Github仓库地址 CSDN博客地址
在开始本题之前,可以先看看这篇文章树的基本知识以及种种遍历方法。
本题目就是使用前序遍历,可以使用 递归的方法,和迭代的方法进行前序遍历(具体方法在链接里面树的基本知识以及种种遍历方法),同时在相应的地方添加括号
首先我们需要知道括号的添加的情况
- 如果当前节点有两个子节点,则在两个子节点的外层添加括号
- 如果当前节点没有任何节点,则不需要添加任何的括号
- 如果当前节点只有左节点,则只在左节点的结果添加括号
- 如果当前节点只有右节点,则需要在前方添加一个
()
之后再添加节点的值
递归方法
class Solution {
public:
// 创建 一个空字符串,用来统计结果
string res = "";
string tree2str(TreeNode *root) {
dfs(root);
// 截取相应的字符串
return res.substr(1, res.size() - 2);
}
// 创建递归函数
void dfs(TreeNode *root) {
// 如果节点是空的就跳出递归
if (root == nullptr) return;
// 将每次前序遍历都套上括号
res += "(";
// 并将相应的值加入到字符串中
res += to_string(root->val);
// 讨论各种情景
if (root->left != nullptr) dfs(root->left);
else if (root->right != nullptr) res += "()";
if (root->right != nullptr) dfs(root->right);
res += ")";
}
};
class Solution {
// 创建 一个空字符串,用来统计结果
String res = "";
public String tree2str(TreeNode root) {
dfs(root);
return res.substring(1, res.length() - 1);
}
// 创建递归函数
public void dfs(TreeNode root) {
// 如果节点是空的就跳出递归
if (root == null) return;
// 将每次前序遍历都套上括号
res += "(";
// 并将相应的值加入到字符串中
res += Integer.toString(root.val);
// 讨论各种情景
if (root.left != null) dfs(root.left);
else if (root.right != null) res += "()";
if (root.right != null) dfs(root.right);
res += ")";
}
}
迭代
迭代的方法与树的前序遍历的迭代方法逻辑一样,
- 如果节点有两个子节点,则先将右节点放入栈中,再将左节点放入栈中
- 如果节点没有任何的子节点,就不对栈进行任何操作
- 如果只有一个左节点,就将左节点放入栈中
- 如果只有一个右节点,就先再结果末尾添加一对括号,再将右节点放入栈中
class Solution {
public:
string tree2str(TreeNode *root) {
string res = "";
// 创建栈用于存储各个节点用于模拟树的前序遍历
stack<TreeNode *> st;
// 放入头节点
st.push(root);
set<TreeNode *> visited;
while (!st.empty()) {
// 将当前节点放入栈中
TreeNode *node = st.top();
// 如果当前节点被访问过,说明以该节点为根节点的子树已经遍历完成
if (!visited.count(node)) {
// 添加括号,并且从栈中移除当前节点
if (node != root) res += ")";
st.pop();
} else {
// 如果没有被访问过,就开始添加新的括号,并将子节点加入栈中
if (node != root) res += "(";
res += node->val;
if (node->left == nullptr && node->right != nullptr) res += "()";
if (node->right != nullptr) st.push(node->right);
if (node->left != nullptr) st.push(node->left);
}
}
return res;
}
};
class Solution {
public String tree2str(TreeNode root) {
String res = "";
// 创建栈用于存储各个节点用于模拟树的前序遍历
Deque<TreeNode> st = new ArrayDeque<TreeNode>();
// 放入头节点
st.push(root);
Set<TreeNode> visited = new HashSet<>();
while (!st.isEmpty()) {
// 将当前节点放入栈中
TreeNode node = st.peek();
// 如果当前节点被访问过,说明以该节点为根节点的子树已经遍历完成
if (!visited.add(node)) {
// 添加括号,并且从栈中移除当前节点
if (node != root) res += ")";
st.pop();
} else {
// 如果没有被访问过,就开始添加新的括号,并将子节点加入栈中
if (node != root) res += "(";
res += node.val;
if (node.left == null && node.right != null) res += "()";
if (node.right != null) st.push(node.right);
if (node.left != null) st.push(node.left);
}
}
return res;
}
}