因为一开始给出的是中序遍历 所以这其实是一道区间dp。。。
dp的同时记一下每个点的儿子就可以完成第二问


#include<iostream> #include<cstdio> using namespace std; int a[32],n,f[32][32],crf[32][32]; long long work(int l,int r) { int k; if (crf[l][r]) return crf[l][r]; if (l>r) return 1; if (l==r) return a[l]; long long res=0,temp=0; int root=0; for (k=l;k<=r;k++) {temp=work(l,k-1)*work(k+1,r)+a[k]; if (temp>res) {res=temp;root=k;} crf[l][r]=res; f[l][r]=root;} return res; } void doit(int l,int r) { if (l>r) return; if (l==r) {cout<<l<<' ';return;} int root=f[l][r]; cout<<root<<' '; doit(l,root-1); doit(root+1,r); } int main() { cin>>n; for (int i=1;i<=n;i++) cin>>a[i]; cout<<work(1,n)<<endl; doit(1,n); }
本文介绍了一种使用区间动态规划(DP)方法解决由中序遍历序列构建最大权值二叉树的问题。通过递归地寻找子树根节点并计算子树的权值,实现了在构建最优二叉树的同时记录每个节点的子节点信息,以完成后续的树形结构输出。文章提供了一个C++实现示例,包括主函数、递归计算函数和树形结构输出函数。
1208

被折叠的 条评论
为什么被折叠?



