#include <iostream>
#include <algorithm>
#include <queue>
using namespace std;
const int content = 50;
struct node{
int data;
node *lchild;
node* rchild;
};
int post[content];
int in[content];
node* create(int postL,int postR,int inL,int inR){
if(postL>postR){
return NULL;
}
node* root = new node;
root->data = post[postR];
int k;
for(int i =inL;i<=inR;i++){
if(in[i]==post[postR]){
k=i;
break;
}
}
//此时k是分水岭
int numLeft = k -inL;
root->lchild = create(postL,postL+numLeft-1,inL,k-1);
// root->lchild = create(postL,postL+numLeft-1,inL,k-1);
root->rchild = create(postL+numLeft,postR-1,k+1,inR);
return root;
}
int sum = 0;
int N;
void BFS(node* root){
queue<node*> q;
q.push(root);
while(!q.empty()){
node* Node = q.front();
q.pop();
cout<<Node->data;
sum++;
if(sum<N){
cout<<" ";
}
if(Node->lchild!=NULL){
q.push(Node->lchild);
}
if(Node->rchild!=NULL){
q.push(Node->rchild);
}
}
}
int main() {
cin>>N;
for(int i =0;i<N;i++){
cin>>post[i];
}
for(int i =0;i<N;i++){
cin>>in[i];
}
node* root = create(0,N-1,0,N-1);
BFS(root);
return 0;
}
//难点 通过后序 中序建立树
其中难点有2:
1.
root->lchild = create(postL,postL+numLeft-1,inL,k-1);
root->rchild = create(postL+numLeft,postR-1,k+1,inR);
递归遍历左子树的后序 区间是 postL postL+numLeft-1 直观理解没问题 就是左边界+左子树结点+1就是又边界,但是这时候我们一定有疑问,为何都求出k了,为什么不让postL+k-1作为右边界呢?如果换成
root->lchild = create(postL,postL+k-1,inL,k-1);程序是会崩溃的。why?
首先 第一次程序运行 确实numleft=k-inL =k但是后面呢?每次递归时候inL的边界可不一定都是0,所以边界是不能用k来衡量 要用k-inL来衡量。
2.
BFS遍历 老生常谈了 队列就完事了。注意格式即可。