L2-006 树的遍历 (25分)
给定一棵二叉树的后序遍历和中序遍历,请你输出其层序遍历的序列。这里假设键值都是互不相等的正整数。
输入格式:
输入第一行给出一个正整数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
解题
由后序,中序可得先序(通过dfs),同时dfs搜索时建立数的结构,
然后用bfs遍历得到层序遍历
代码
#include <iostream>
#include <algorithm>
#include <vector>
#include <queue>
using namespace std;
const int maxn = 1e2 + 2;
vector<int> v_forward, v_mid, v_back;
vector<int> v_layer;
typedef struct TNode {
int value;
TNode *left, *right;
} * Tree;
Tree dfs(int lm, int rm, int lb, int rb, Tree T) { //中序遍历, 后序遍历表示的区间
if(lm > rm) return T;
if(!T) T = new TNode();
T->value = v_back[rb];
int k = lm;
for(int i = lm; i <= rm; i++) { // 已知后序, 遍历中序
if(v_mid[i] == v_back[rb]) {
k = i;
break;
}
}
int lenA = k - lm;
int lenB = rm - k;
v_forward.push_back(v_back[rb]);
T->left = dfs(lm, k - 1, lb, lb + lenA - 1, T->left);
T->right = dfs(k + 1, rm, rb - lenB, rb - 1, T->right);
return T;
}
void bfs(Tree startT) {
queue<Tree> q;
q.push(startT);
while(!q.empty()) {
Tree T = q.front();
v_layer.push_back(T->value);
q.pop();
if(T->left)
q.push(T->left);
if(T->right)
q.push(T->right);
}
}
int main() {
int N, a;
cin >> N;
for(int i = 0; i < N; i++) {
cin >> a;
v_back.push_back(a);
}
for(int i = 0; i < N; i++) {
cin >> a;
v_mid.push_back(a);
}
Tree T;
T = dfs(0, v_mid.size() - 1, 0, v_back.size() - 1, NULL); //dfs可得先序遍历
// cout << T << endl;
// cout << T->left << endl;
// cout << T->right << endl;
bfs(T);
// for(int i = 0; i < v_forward.size(); i++) {
// if(i) cout << " ";
// cout << v_forward[i];
// }
// cout << v_layer.size() << endl;
for(int i = 0; i < v_layer.size(); i++) {
if(i) cout << " ";
cout << v_layer[i];
}
return 0;
}