PAT:1086. Tree Traversals Again (25) AC
#include<stdio.h>
#include<string.h>
#include<stack>
using namespace std;
const int MAX=50;
int n,cnt=0; //n个节点,cnt在后序输出的时候控制空格数量用
int PRE[MAX],IN[MAX]; //先序,中序
int preI,inI; //先序,中序的下标
stack<int> S; //栈
struct node
{
int data;
node* l;
node* r;
};
node* create(int preL,int preR,int inL,int inR)
{
if(preL>preR)
return NULL;
node* root=new node;
root->data=PRE[preL];
root->l=NULL;
root->r=NULL;
int k;
for(k=inL ; k<=inR ; ++k) //在中序找到这个节点
if(IN[k]==root->data)
break;
int numleft=k-inL; //此节点左子树个数
root->l=create(preL+1,preL+numleft,inL,k-1); //【caution】下一轮先序下标到preL+numleft。
root->r=create(preL+numleft+1,preR,k+1,inR);
return root;
}
void postorder(node* root)
{
if(root==NULL)
return;
postorder(root->l);
postorder(root->r);
printf("%d",root->data);
++cnt;
if(cnt<n)
printf(" ");
}
int main()
{
preI=inI=0;
scanf("%d",&n);
for(int i=0 ; i<2*n ; ++i) //【思维】Push顺序刚好是先序序列,Pop序列刚好是中序序列,可以建立二叉树,然后后序遍历
{
char tmp[5]; //最多为Push,4个char但是\0占一个,至少申请5个char空间
int num; //暂存Push和Pop数
scanf("%s",tmp);
if(strcmp(tmp,"Push")==0) //Push则进栈
{
scanf("%d",&num);
S.push(num);
PRE[preI++]=num; //num也是先序序列数
}
else
{
num=S.top(); //Pop出栈
S.pop();
IN[inI++]=num; //num是中序序列数
}
}
node* root=create(0,inI-1,0,preI-1);
postorder(root);
return 0;
}