P1352 没有上司的舞会
题目描述
某大学有N个职员,编号为1~N。他们之间有从属关系,也就是说他们的关系就像一棵以校长为根的树,父结点就是子结点的直接上司。现在有个周年庆宴会,宴会每邀请来一个职员都会增加一定的快乐指数Ri,但是呢,如果某个职员的上司来参加舞会了,那么这个职员就无论如何也不肯来参加舞会了。所以,请你编程计算,邀请哪些职员可以使快乐指数最大,求最大的快乐指数。
输入格式
第一行一个整数N。(1<=N<=6000)
接下来N行,第i+1行表示i号职员的快乐指数Ri。(-128<=Ri<=127)
接下来N-1行,每行输入一对整数L,K。表示K是L的直接上司。
最后一行输入0 0
输出格式
输出最大的快乐指数。
输入输出样例
输入 #17 1 1 1 1 1 1 1 1 3 2 3 6 4 7 4 4 5 3 5 0 0输出 #15
鬼畜的存表方式qwq。
1 #include<bits/stdc++.h> 2 3 using namespace std; 4 int f[2][6005]; 5 int n,x,y,ro; 6 int fr[12005],ne[12005],fa[12005]; 7 void dp(int x) 8 { 9 for(int i=fr[x];i;i=ne[i]) 10 { 11 dp(i); 12 f[1][x]=max(max(f[1][x],f[0][i]+f[1][x]),f[0][i]); 13 f[0][x]=max(max(f[0][x],f[1][i]+f[0][x]),max(f[0][i],f[1][i])); 14 } 15 } 16 int main() 17 { 18 cin>>n; 19 for(int i=1;i<=n;i++) 20 cin>>f[1][i]; 21 for(int i=1;i<=n;i++) 22 { 23 cin>>x>>y; 24 fa[x]++; 25 ne[x]=fr[y]; 26 fr[y]=x; 27 } 28 for(int i=1;i<=n;i++) 29 if(fa[i]==0) 30 { 31 ro=i; 32 break; 33 } 34 dp(ro); 35 cout<<max(f[1][ro],f[0][ro]); 36 return 0; 37 }
P1040 加分二叉树
题目描述
设一个n个节点的二叉树tree的中序遍历为(1,2,3,…,n),其中数字1,2,3,…,n为节点编号。每个节点都有一个分数(均为正整数),记第i个节点的分数为di,tree及它的每个子树都有一个加分,任一棵子树subtreesubtree(也包含treetree本身)的加分计算方法如下:
subtree的左子树的加分× subtree的右子树的加分+subtree的根的分数。
若某个子树为空,规定其加分为1,叶子的加分就是叶节点本身的分数。不考虑它的空子树。
试求一棵符合中序遍历为(1,2,3,…,n)且加分最高的二叉树tree。要求输出;
(1)tree的最高加分
(2)tree的前序遍历
输入格式
第1行:1个整数n(n<30),为节点个数。
第2行:n个用空格隔开的整数,为每个节点的分数(分数<100)。
输出格式
第1行:1个整数,为最高加分(Ans≤4,000,000,000)。
第2行:n个用空格隔开的整数,为该树的前序遍历。
输入输出样例
输入 #15 5 7 1 2 10输出 #1145 3 1 2 4 5
枚举哪个是根。
1 #include<bits/stdc++.h> 2 #define re register int 3 #define LL long long 4 #define maxn 30+5 5 6 using namespace std; 7 LL f[maxn][maxn]; 8 int root[maxn][maxn]; 9 int n; 10 inline LL dp(int l,int r) 11 { 12 if(f[l][r]) return f[l][r]; 13 for(re k=l+1;k<=r-1;k++) 14 { 15 if(dp(l,k-1)*dp(k+1,r)+f[k][k]>f[l][r]) 16 root[l][r]=k,f[l][r]=dp(l,k-1)*dp(k+1,r)+f[k][k]; 17 } 18 if(dp(l+1,r)+f[l][l]>f[l][r]) 19 root[l][r]=l,f[l][r]=dp(l+1,r)+f[l][l]; 20 if(dp(l+1,r)+f[l][l]>f[l][r]) 21 root[l][r]=l,f[l][r]=dp(l+1,r)+f[l][l]; 22 return f[l][r]; 23 } 24 void print(int l,int r) 25 { 26 if(l==r) { 27 cout<<l<<' '; 28 return; 29 } 30 cout<<root[l][r]<<' '; 31 if(root[l][r]-1>=l) print(l,root[l][r]-1); 32 if(root[l][r]+1<=r) print(root[l][r]+1,r); 33 } 34 int main() 35 { 36 ios::sync_with_stdio(false); 37 cin>>n; 38 for(re i=1;i<=n;i++) 39 cin>>f[i][i]; 40 cout<<dp(1,n)<<endl; 41 print(1,n); 42 }