題目描述
給定一棵二叉樹的後序遍歷和中序遍歷,請你輸出其層序遍歷的序列。這裏假設鍵值都是互不相等的正整數。
輸入格式:
輸入第一行給出一個正整數N(≤30),是二叉樹中結點的個數。第二行給出其後序遍歷序列。第三行給出其中序遍歷序列。數字間以空格分隔。
輸出格式:
在一行中輸出該樹的層序遍歷的序列。數字間以1個空格分隔,行首尾不得有多餘空格。
輸入樣例:
7
2 3 1 5 7 6 4
1 2 3 4 5 6 7
輸出樣例:
4 1 6 3 5 7 2
思路分析
這種根據前序和中序求後序,後序和中序求前序的題思路大同小異。基本都是先建樹,再按條件輸出。
建樹: 先找到根節點,利用遞歸再找到左子樹的根和右子樹的根,一直到葉節點。
輸出: 四種輸出在我上一篇博客裏面有講解,需要哪一種可以直接把相應的方法copy過來。有一點要注意的是輸出格式要求最後不能有空格,我們可以設置一個變量初始爲0,每次輸出+1,在輸出之前判斷一下,如果不爲0,就多輸出一個空格。這樣除了第一個前面沒有空格,其他前面都有空格,就符合要求了。
源代碼
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
typedef struct TNode* BinTree;
struct TNode{
int Data;
BinTree Left;
BinTree Right;
};
BinTree getTree(int a[],int b[],int sum);
void Preorder(BinTree BT);
void LevelorderTraversal( BinTree BT ,int n);
int main(){
int n;
scanf("%d",&n);
int a[n],b[n];
for (int i = 0; i < n; i++) {
scanf("%d",&a[i]);
}
for (int j = 0; j < n; j++) {
scanf("%d",&b[j]);
}
BinTree BT=getTree(a,b,n);
LevelorderTraversal(BT,n);
return 0;
}
BinTree getTree(int a[],int b[],int sum){
int i;
BinTree BT;
if(sum==0)
return NULL;
else{
BT=(BinTree)malloc(sizeof(struct TNode));
BT->Data=a[sum-1];
for (i = 0; i < sum; i++) {
if(b[i]==a[sum-1])
break;
}
BT->Left=getTree(a,b,i);
BT->Right=getTree(a+i,b+1+i,sum-i-1);
}
return BT;
}
void Preorder(BinTree BT){
if(BT){
printf(" %d",BT->Data);
Preorder(BT->Left);
Preorder(BT->Right);
}
}
void LevelorderTraversal( BinTree BT ,int n){//層序
if(!BT)
return;
int len=1,pos,sum=0;
BinTree a[101],b[101];
a[0]=BT;
while(1){
if(len==0)
return;
pos=0;
for(int i=0;i<len;i++)
{
if(a[i]->Left!=NULL)//如果它的左節點不爲空,就存到b數組裏
b[pos++]=a[i]->Left;
if(a[i]->Right!=NULL)//如果它的右節點不爲空,就存到b數組裏
b[pos++]=a[i]->Right;
if(a[i]!=NULL){//不爲空輸出
printf("%d",a[i]->Data);
sum++;
}
if(sum!=n)
printf(" ");
}
len=pos;//更新下一層寬度,爲下一次循環做準備
for(int i=0;i<len;i++)//將下層的b賦給a,爲下一次循環做準備
a[i]=b[i];
}
}