[HAOI2015] [bzoj4033] [T1], haoi2015bzoj4033
4033: [HAOI2015] T1
Time Limit: 10 Sec Memory Limit: 256 MB
Submit: 226 Solved: 111
[Submit] [Status] [Discuss]
Description
A tree with N points has Edge Weight. You can get one from 0 ~ Positive Integers within N
K, you need to select K points in the tree, dye them into black, and
N-K points Dyed white. After dyeing all vertices, you will get the distance between the two black spots.
Benefit from the sum of the distance between the two white points. Ask the maximum benefit.
Input
The first line contains two integers, N and K.
Next, each row of the N-1 line has three positive integers fr, to, dis, indicating that there is a length in the tree
Is the edge of dis (fr, ). Input to ensure that all vertices are connected.
Output
Returns a positive integer that represents the maximum benefit.
Sample Input
3 1
1 2 1
1 3 2
Sample Output
3
HINT
For 100% of data, 0 <= K <= N <= 2000
Problem: it is easy to think of the greatest benefit when k Subtrees of the I node are dyed black with f [I] [j.
However, in this way, we can only process The Situation in the subtree, and there is no way to do it outside the subtree, so we need to define the state again.
F [I] [j] indicates the contribution to the answer. In this way, we only need to multiply the numbers of black points and white points in the subtree apart from the word count, just take the weight on the road.
#include<iostream>#include<cstdio>#include<cstring>#define LL long longusing namespace std;const int N=2100;int n,k,tot=1,point[N],next[N*4],siz[N];long long f[N][N];struct S{ int st,en,va;}aa[N*4];inline void add(int x,int y,int z){ tot+=1;next[tot]=point[x];point[x]=tot; aa[tot].st=x;aa[tot].en=y;aa[tot].va=z; tot+=1;next[tot]=point[y];point[y]=tot; aa[tot].st=y;aa[tot].en=x;aa[tot].va=z;}inline void dp(int x,int fa){ int i,j,u,l; siz[x]=1; f[x][0]=f[x][1]=0; for(i=point[x];i;i=next[i]) if(aa[i].en!=fa){ u=aa[i].en; dp(u,x); siz[x]+=siz[u]; for(j=siz[x];j>=0;--j) for(l=0;l<=min(siz[u],j);++l) f[x][j]=max(f[x][j],f[x][j-l]+((LL)(l*(k-l))+(LL)(siz[u]-l)*(LL)(n-k-(siz[u]-l)))*(LL)aa[i].va+f[u][l]); }}int main(){ int i,j,x,y,z; scanf("%d%d",&n,&k); memset(f,128,sizeof(f)); for(i=1;i<n;++i){ scanf("%d%d%d",&x,&y,&z); add(x,y,z); } dp(1,0); cout<<f[1][k]<<endl;}