C++非递归二叉树的先序遍历
#include <iostream>
#include <algorithm>
#include<vector>
#include<stack>
using namespace std;
struct BTree{
int val;
BTree *left,*right;
BTree(){}
BTree(int x){val=x;left=NULL;right=NULL;}
BTree(int x,BTree*node1,BTree *node2){val=x;left=node1;right=node2;}
};
void visitN(BTree *root){
stack<BTree *> st;//定义一个栈,用来模拟递归
//stack<BTree *> res;
vector<int> res;
BTree *BT=root;//当前遍历所在节点
while(BT||!st.empty()){//如果当前为空节点且栈也为空,退出循环
while(BT){//当前结点非空
st.push(BT);//入栈
res.push_back(BT->val);
BT=BT->left;//访问左结点
}
//如果节点为空,从栈中取出一个节点
if(!st.empty()){
BT=st.top();
st.pop();
//进入右节点
BT=BT->right;
}
}
//输出结果
for(int num:res){
cout<<num<<" ";
}
}
int main(){
BTree *head4=new BTree(1);
BTree *head3=new BTree(2);
BTree *head2=new BTree(3,NULL,head4);
BTree *head1=new BTree(4,head3,NULL);
BTree *head=new BTree(5,head1,head2);
visitN(head);
}
C++非递归二叉树的中序遍历,其实只有输出res.push_back(BT->val);位置换了一下
#include <iostream>
#include <algorithm>
#include<vector>
#include<stack>
using namespace std;
struct BTree{
int val;
BTree *left,*right;
BTree(){}
BTree(int x){val=x;left=NULL;right=NULL;}
BTree(int x,BTree*node1,BTree *node2){val=x;left=node1;right=node2;}
};
void visitN(BTree *root){
stack<BTree *> st;//定义一个栈,用来模拟递归
//stack<BTree *> res;
vector<int> res;
BTree *BT=root;//当前遍历所在节点
while(BT||!st.empty()){//如果当前为空节点且栈也为空,退出循环
while(BT){//当前结点非空
st.push(BT);//入栈
BT=BT->left;//访问左节点
}
//如果节点为空,从栈中取出一个节点
if(!st.empty()){
BT=st.top();
res.push_back(BT->val);//这部才是访问节点,从栈中取出节点才访问
st.pop();
//进入右节点
BT=BT->right;
}
}
//输出结果
for(int num:res){
cout<<num<<" ";
}
}
int main(){
BTree *head4=new BTree(1);
BTree *head3=new BTree(2);
BTree *head2=new BTree(3,NULL,head4);
BTree *head1=new BTree(4,head3,NULL);
BTree *head=new BTree(5,head1,head2);
visitN(head);
}
先序遍历,访问节点的顺序是头左右,后序遍历访问的顺序是左右头
此时将先序遍历的左右节点访问顺序颠倒一下,变成头右左,再整体逆序,就是左右头 ,就是后续遍历了,所以代码在此基础上修改
#include <iostream>
#include <algorithm>
#include<vector>
#include<stack>
using namespace std;
struct BTree{
int val;
BTree *left,*right;
BTree(){}
BTree(int x){val=x;left=NULL;right=NULL;}
BTree(int x,BTree*node1,BTree *node2){val=x;left=node1;right=node2;}
};
void visitN(BTree *root){
stack<BTree *> st;//定义一个栈,用来模拟递归
//stack<BTree *> res;
vector<int> res;
BTree *BT=root;//当前遍历所在节点
while(BT||!st.empty()){//如果当前为空节点且栈也为空,退出循环
while(BT){//当前结点非空
st.push(BT);//入栈
res.push_back(BT->val);//跟先序的访问位置一样
BT=BT->right;//左右互换
}
//如果节点为空,从栈中取出一个节点
if(!st.empty()){
BT=st.top();
st.pop();
//进入左节点
BT=BT->left;//左右互换
}
}
//将此时的res逆置就是后序遍历的访问顺序了
reverse(res.begin(),res.end());
//输出结果
for(int num:res){
cout<<num<<" ";
}
}
int main(){
BTree *head4=new BTree(1);
BTree *head3=new BTree(2);
BTree *head2=new BTree(3,NULL,head4);
BTree *head1=new BTree(4,head3,NULL);
BTree *head=new BTree(5,head1,head2);
visitN(head);
}
层次遍历
#include <iostream>
#include <algorithm>
#include<vector>
#include<stack>
#include<deque>
using namespace std;
struct BTree{
int val;
BTree *left,*right;
BTree(){}
BTree(int x){val=x;left=NULL;right=NULL;}
BTree(int x,BTree*node1,BTree *node2){val=x;left=node1;right=node2;}
};
void visitN(BTree *root){
if(root==NULL)return;
deque<BTree*> queue;//队列,用来存储节点数据,
vector<int> res;
BTree *BT=root;
BTree *node;
queue.push_back(BT);//先将头结点入队
while(!queue.empty()){//当队列不空,将队头出队
node=queue.front();
res.push_back(node->val);
queue.pop_front();
if(node->left){//若孩子存在,则将孩子入队
queue.push_back(node->left);
}
if(node->right){
queue.push_back(node->right);
}
}
//输出结果
for(int num:res){
cout<<num<<" ";
}
}
int main(){
BTree *head4=new BTree(1);
BTree *head3=new BTree(2);
BTree *head2=new BTree(3,NULL,head4);
BTree *head1=new BTree(4,head3,NULL);
BTree *head=new BTree(5,head1,head2);
visitN(head);
}
计算二叉树的最大宽度,感觉左神的方法太复杂了,用一个简易版的层次遍历+哈希表很容易就得出来了(也不算层次遍历,只是用了层数的概念)
#include <iostream>
#include <algorithm>
#include <vector>
#include <stack>
#include <deque>
#include <unordered_map>
using namespace std;
struct BTree
{
int val;
BTree *left, *right;
BTree() {}
BTree(int x)
{
val = x;
left = NULL;
right = NULL;
}
BTree(int x, BTree *node1, BTree *node2)
{
val = x;
left = node1;
right = node2;
}
};
unordered_map<int, int> map;//用来存储每一行的结点数
//本来以为是层次遍历的,但是写着发现其实不太算层次,只是用了层数的概念
void visitN(BTree *root, int layer)
{
if (root == NULL)
return;
map[layer]++;
BTree *BT = root;
visitN(BT->left, layer + 1);
visitN(BT->right, layer + 1);
}
int main()
{
BTree *head5 = new BTree(10);
BTree *head4 = new BTree(1);
BTree *head3 = new BTree(2);
BTree *head2 = new BTree(3, head5, head4);
BTree *head1 = new BTree(4, head3, NULL);
BTree *head = new BTree(5, head1, head2);
visitN(head, 0);
int index = 0, max = 0;
for (auto num : map)
{
if (max < num.second)
{
max = num.second;
index = num.first;
}
}
cout << "layer=" << index << ",num=" << max;
}