Leetcode刷题笔记(C++)——二叉树
整理一下刷题过程中的思路,在这里进行一下总结与分享。
github地址:https://github.com/lvjian0706/Leetcode-solutions
github项目是刚刚新建的,陆续会将整理的代码以及思路上传上去,代码是基于C++与python的。同时会将基础的排序算法等也一并进行整理上传。
102. 二叉树的层序遍历
给你一个二叉树,请你返回其按 层序遍历 得到的节点值。 (即逐层地,从左到右访问所有节点)。
示例:
二叉树:[3,9,20,null,null,15,7],
3
/
9 20
/
15 7
返回其层次遍历结果:
[
[3],
[9,20],
[15,7]
]
/**
* Definition for a binary tree node.
* struct TreeNode {
* int val;
* TreeNode *left;
* TreeNode *right;
* TreeNode(int x) : val(x), left(NULL), right(NULL) {}
* };
*/
class Solution {
public:
/*
层序遍历:宽度优先搜索(bfs)
1. 创建队列存放二叉树的节点以及节点对应的level,其中使用pair来存放二叉树的节点以及节点对应的level;
2. 如果树为空,返回空ans数组;
3. 首先将<root, 0>进栈,并且定义idx为当前level;
4. 循环遍历队头中的元素:
4.1 使用pnode存储队头元素,保存队头元素的值以及level,并将队头元素出栈;
4.2 判断队头元素的level与idx是否一致,一致说明队头元素与之前的元素属于相同的level,直接push进subAns;否则说明队头元素与之前的元素属于不同的level,更新idx,先将subAnspush进ans中,再清空subAns,并将队头元素的值push进去;
4.3 判断是否还有左右孩子,有的话将左右孩子和对应的level(nowIdx+1)存入队列;
5. 将最后一组subAns的值push进ans中,返回ans;
*/
vector<vector<int>> levelOrder(TreeNode* root) {
queue<pair<TreeNode*, int>> qnode;
vector<vector<int>> ans;
if(!root) return ans;
vector<int> subAns;
qnode.push(make_pair(root, 0));
int idx = 0;
while(!qnode.empty()){
pair<TreeNode*, int> pnode = qnode.front();
qnode.pop();
TreeNode* node = pnode.first;
int nowIdx = pnode.second;
if(nowIdx != idx){
ans.push_back(subAns);
subAns.clear();
idx = nowIdx;
}
subAns.push_back(node->val);
if(node->left) qnode.push(make_pair(node->left, nowIdx+1));
if(node->right) qnode.push(make_pair(node->right, nowIdx+1));
}
ans.push_back(subAns);
return ans;
}
};
103. 二叉树的锯齿形层次遍历
给定一个二叉树,返回其节点值的锯齿形层次遍历。(即先从左往右,再从右往左进行下一层遍历,以此类推,层与层之间交替进行)。
例如:
给定二叉树 [3,9,20,null,null,15,7],
3
/
9 20
/
15 7
返回锯齿形层次遍历如下:
[
[3],
[20,9],
[15,7]
]
/**
* Definition for a binary tree node.
* struct TreeNode {
* int val;
* TreeNode *left;
* TreeNode *right;
* TreeNode(int x) : val(x), left(NULL), right(NULL) {}
* };
*/
class Solution {
public:
/*
层序遍历:宽度优先搜索(bfs)
1. 创建队列存放二叉树的节点以及节点对应的level,其中使用pair来存放二叉树的节点以及节点对应的level;
2. 如果树为空,返回空ans数组;
3. 首先将<root, 0>进栈,并且定义idx为当前level;
4. 定义flag变量用于判断当前行是从左往右还是从右往左进行遍历;
5. 循环遍历队头中的元素:
5.1 使用pnode存储队头元素,保存队头元素的值以及level,并将队头元素出栈;
5.2 判断队头元素的level与idx是否一致,一致说明队头元素与之前的元素属于相同的level,通过flag的状态判断是将当前元素push到数组末尾还是insert到数组头部;
5.3. 否则说明队头元素与之前的元素属于不同的level,更新idx,先将subAns插入ans的第一个位置,再清空subAns,并通过flag的状态判断是将当前元素push到数组末尾还是insert到数组头部;;
5.4 判断是否还有左右孩子,有的话将左右孩子和对应的level(nowIdx+1)存入队列;
6. 将最后一组subAns的值插入ans的第一个位置,返回ans;
*/
vector<vector<int>> zigzagLevelOrder(TreeNode* root) {
vector<vector