Description
给一棵点带权(权值各不相同,都是小于20000的正整数)的二叉树的中序和后序遍历,找一个叶子使得他到根的路径上的权值和最小。如果有多解,该叶子本身的权应尽量小。
Input
输入包含多组数据,每组数据含两行,其中第一行为中序遍历,第二行为后序遍历,序列中的数字代表对应节点的权值。
Output
一个整数,表示所求的叶子节点的权值。
Sample Input 1
3 2 1 4 5 7 6
3 1 2 5 6 7 4
7 8 11 3 5 16 12 18
8 3 11 7 16 18 12 5
255
255
Sample Output 1
1
3
255
Hint
树的节点数不超过10000。
读入处理
#include<cstdio> #include<iostream> #include<cstring> #include<sstream> #define maxn 10005 #define maxm 20005 using namespace std; typedef long long ll; int A[maxn], B[maxn]; int lch[maxm], rch[maxm]; int wz[maxm]; int n; bool data_in(int *a){ string str; if(!getline(cin,str)) return false; stringstream ss(str); n = 0; int x; while(ss>>x) a[++n] = x; return n > 0; } int build(int r1,int l1,int r2,int l2){ if(r1>l1) return 0; int root = B[l2]; int p = wz[root], cnt = p-r1; lch[root] = build(r1,p-1,r2,r2+cnt-1); rch[root] = build(p+1,l1,r2+cnt,l2-1); return root; } int best , best_sum; void dfs(int u,int sum){ sum += u; if(!lch[u] && !rch[u]){ if(sum<best_sum ||(sum==best_sum&&u<best)) best = u, best_sum = sum; return; } if(lch[u]) dfs(lch[u],sum); if(rch[u]) dfs(rch[u],sum); } int main(){ while(data_in(A)){ data_in(B); for(int i=1;i<=n;i++) wz[A[i]] = i; build(1, n, 1, n); best_sum = 200000000; dfs(B[n],0); printf("%d ", best); } return 0; }