[NOIP 2003] 加分二叉树:DP
来源:互联网 发布:网络推广工资高吗 编辑:程序博客网 时间:2024/05/19 19:33
题意:定义一棵二叉树的加分是所有结点的加分之和。叶子的加分是它的权值;非叶子结点的加分=左子树加分*右子树加分+根的权值,式中的子树不存在则取1。给定n个结点的权值(n<=30),求所有中序遍历为1, 2, …, n的二叉树的最大加分,并输出其前序遍历。
同一个中序遍历可能对应着很多棵二叉树。怎样确定一棵呢?加括号。
有一点略奇怪……通常而言,输出方案,又没对输出哪一组做出规定,应该用Special Judge才行。但是这道题似乎没出现什么问题。也许数据经过特殊构造?
#include <cstdio>#include <algorithm>#include <cstring>using namespace std;typedef unsigned un;const int MAX_N = 30;un v[MAX_N+1], f[MAX_N+2][MAX_N+2];int p[MAX_N+1][MAX_N+1];void build(int i, int j){ if (i > j) return; printf("%d ", p[i][j]); build(i, p[i][j]-1); build(p[i][j]+1, j);}int main(){ int n; scanf("%d", &n); for (int i = 1; i <= n; ++i) scanf("%u", &v[i]); for (int i = 1; i <= n+1; ++i) f[i][i-1] = 1; // f[i][j] = max { f[i][k-1] * f[k+1][j] + v[k] } for (int i = n; i >= 1; --i) { f[i][i] = v[i]; p[i][i] = i; for (int j = i+1; j <= n; ++j) for (int k = i; k <= j; ++k) if (f[i][k-1]*f[k+1][j] + v[k] > f[i][j]) { f[i][j] = f[i][k-1] * f[k+1][j] + v[k]; p[i][j] = k; } } printf("%u\n", f[1][n]); build(1, n); puts(""); return 0;}
0 0
- [NOIP 2003] 加分二叉树:DP
- NOIP 2003 加分二叉树
- NOIP 2003 加分二叉树
- Noip 2003 加分二叉树
- Noip 2003 加分二叉树
- 加分二叉树 noip
- Noip 2003T3 加分二叉树
- [NOIP提高组2003]加分二叉树
- 加分二叉树 2003年NOIP全国联赛提高组
- 加分二叉树 2003年NOIP全国联赛提高组
- 加分二叉树[NOIP 2003提高组][Codevs 1090]
- 「2003NOIP提高组」加分二叉树
- NOIP 2003 提高组 复赛 加分二叉树
- 加分二叉树 树型DP
- 加分二叉树 树形DP
- noip2003 加分二叉树 dp
- 加分二叉树 区间dp
- 树形dp 加分二叉树 / 11.05.15
- Java分解URL
- 第八周OJ5打印数字图形
- 从零开始学C++之运算符重载(四):类型转换运算符、*运算符重载、->运算符重载、operator new 和 operator delete
- 有1,2,3,4这四个数,能组成多少互补相同且无重复的三位数字,都是多少?
- 深入理解struts的运行机制
- [NOIP 2003] 加分二叉树:DP
- Codeforces 731F By Assassin
- Python大数据之numpy
- 压缩和解压缩命令
- [leetcode]141. Linked List Cycle
- 【C++】容器迭代器使用中出现的程序中断
- visualvm监控jvm及远程jvm监控方法
- 第七周项目求一元二次方程根
- HttpURLConnection 中参数的构建方式 引起的 500错误