199 Binary Tree Right Side View
/**
* Definition for a binary tree node.
* struct TreeNode {
* int val;
* TreeNode *left;
* TreeNode *right;
* TreeNode() : val(0), left(nullptr), right(nullptr) {}
* TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
* TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {}
* };
*/
class Solution {
public:
vector<int> rightSideView(TreeNode* root) {
//给出每一层最右边的结点的值
//层次遍历yyds
if(!root) return {};
vector<int> ans;
queue<TreeNode*> que;
que.push(root);
while(!que.empty()){
int n = que.size();
for(int i = 0 ; i < n ; i++){
TreeNode* node = que.front();
//读取最后一个
if(i == n-1){
ans.push_back(node->val);
}
que.pop();
if(node->left) que.push(node->left);
if(node->right) que.push(node->right);
}
}
return ans;
}
};
331 Verify Preorder Serialization of a Binary Tree
难点:如何判定二叉树有效
易错点:将多位数字拆开分析,如下列第一块代码
331 错误示例:1.将多位数字拆开2.仍然使用遍历树的方式,典型不听劝【这道题不需要用遍历树的结构思路去解答,会比较麻烦,也不易得到简洁的思路】
class Solution {
public:
int helper(vector<char>& pre ,int a){
if(a>=pre.size()) return -1;//是否超界
if(pre[a]== '#')return a+1;
int left = helper(pre,a+1);//处理左子树
if(left == -1) return -1;
int right = helper(pre,left);//处理右子树
if(right == -1) return -1;
return right;
}
bool isValidSerialization(string preorder) {
vector<char> pre;
for(char ch : preorder){
if(ch!=',')pre.push_back(ch);
}
int end = helper(pre,0);
return end == pre.size();
}
};
上述代码修改提交,勉强通过,耗时很长:
class Solution {
public:
int helper(vector<string>& pre, int a) {
if (a >= pre.size()) return -1; // 超界,返回 -1
if (pre[a] == "#") return a + 1; // 如果是空节点,返回下一个节点位置
int left = helper(pre, a + 1); // 处理左子树
if (left == -1) return -1; // 如果左子树非法,返回 -1
int right = helper(pre, left); // 处理右子树
if (right == -1) return -1; // 如果右子树非法,返回 -1
return right; // 返回下一个未处理的节点索引
}
bool isValidSerialization(string preorder) {
vector<string> pre;
stringstream ss(preorder);
string token;
// 使用 stringstream 按照逗号分割字符串,生成字符串列表
while (getline(ss, token, ',')) {
pre.push_back(token);
}
int end = helper(pre, 0);
return end == pre.size();
}
};
正确/简洁思路:
class Solution {
public:
bool isValidSerialization(string preorder) {
int slots = 1; //根节点有一个槽位
int n = preorder.size();
for(int i = 0 ; i < n ;i++){
if(preorder[i] == ',')continue;
//遇到一个节点,无论空或非空 都减少一个槽位
--slots;
//如果槽数为负数,序列无效
if(slots < 0) return false;
if(preorder[i] != '#'){
while(i < n && preorder[i] !=',') ++i;//跳过多位数字
slots+=2;
}
}
return slots == 0;
}
};