给定一棵二叉树的后序遍历和中序遍历,请你输出其层序遍历的序列。这里假设键值都是互不相等的正整数。
输入格式:
输入第一行给出一个正整数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
知识点
前序遍历:根左右
中序遍历:左根右
后序遍历:左右根
思路:
root:当前树在后序遍历中根的位置
start:当前树在中序遍历中开始的位置
end:当前树在中序遍历中结束的位置
index:当前子树根所在位置数
则可知后序遍历中2 3 1 5 7 6 4末尾4为根,想知道“左右根”中左右子树分界,则可求出中序遍历中根的位置i,求出右子树的数目end-i
左子树:
根在后序遍历中位置root-1-(end-i)
在中序遍历中从start到i-1
右子树:
根位于前序遍历中位置root+(i-start+1)
在中序遍历中从i+1到end
运用递归,求出二叉树
二叉树
代码:
#include<iostream>
#include<algorithm>
#include<cstring>
#include<vector>
using namespace std;
vector<int> last,mid,level(100000,-1);
void fun(int root,int start,int end,int index){
//后序:左右根,根为后续遍历最后一个数root
//中序:左根右, 在中序遍历中从start到end寻找root,将root左右两边分为左子树,右子树
int i=start;
if(start>end)
return;
while(i<end&&mid[i]!=last[root]) i++;//i为中序遍历中根的位置
level[index]=last[root];;
fun(root-1-end+i,start,i-1,2*index+1);//2*index+1,index的左子树
//end-i为中序遍历右子树大小
//root-1-(end-i)为后序遍历:左右根-根-有=左子树
fun(root-1,i+1,end,2*index+2);//2*index+2,index的右子树
//根为右子树后续遍历root左边的数,求左子树
}
int main(){
int n;
cin>>n;
last.resize(n);
mid.resize(n);
for(int i=0;i<n;i++)
cin>>last[i];
for(int i=0;i<n;i++)
cin>>mid[i];
fun(n-1,0,n-1,0);
for(int i=0,cnt=0;i<level.size();i++){
if(level[i]!=-1){
cout<<level[i];
if(cnt!=n-1) cout<<" ";
cnt++;
}
}
return 0;
}