srm666 div1 222
博客里以前都是记载的不会的,但是这道题不得不记载,因为最简单的一道题写了一下午,但还是很开心,因为一开始感觉这道题我绝对做不出来,还伤心的怀疑自己的智商,可是硬着头皮做下来,发现,没有人把刀架脖子上逼着我不准写,为啥不写呢?写
思路:感觉有点想树形dp,挺简单的。只要分一下返回不返回就行了。
发的是调试时用的代码,所以没有写成类。
(这次没有参考链接,今天和队友又去吃了那个有头发和虫子的明味家,虽然卫生……,但是很好吃,在此,不得不又一个严肃的问题,生命和胃那个更重要?)
/* 2015/8/28 20:26 srm666 div1 222 (67.48)
zhangboyu */ #include<stdio.h> #include<string.h> #include<iostream> using namespace std; #define N 60 #define M 110 int dph[N][M]; int dpb[3][N][M]; int head[N],to[2*N],nextedge[2*N];//head明明没有改变值,却产生变化,可能是因为它前面的那个数组出了问题,可能是开小了 int cou=0; int L; void add(int a,int b){ to[cou]=b;nextedge[cou]=head[a];head[a]=cou++; } void dfs(int u,int fa){ for(int i=0;i<=L;i++){ dph[u][i]=1; } //printf("%d %db\n",u,head[u]); for(int i=head[u];i!=-1;i=nextedge[i]){ int v=to[i]; //printf("%d %d\n",u,v); if(v==fa){ continue; } else{ dfs(v,u); for(int i=L;i>=0;i--){ for(int j=0;j<=i-2;j++){ dph[u][i]=max(dph[u][i],dph[v][j]+dph[u][i-j-2]); } } } } for(int i=0;i<=L;i++){ dpb[2][u][i]=1; } //printf("%d %da\n",u,head[u]); for(int i=head[u];i!=-1;i=nextedge[i]){//枚举走到那个子节点可以不回来 int vb=to[i]; //printf("%d %d %dhehe\n",u,vb,nextedge[i]); if(vb==fa){ continue; } for(int i=0;i<=L;i++){ dpb[1][u][i]=1; } for(int j=head[u];j!=-1;j=nextedge[j]){ int v=to[j]; //printf("%d %d %dhaha\n",u,v,nextedge[j]); if(v==fa){ continue; } if(v==vb){ for(int i=L;i>=0;i--){ for(int j=0;j<=i-1;j++){ //printf("%d %d %d %d %d %d %d %dha\n",u,i,j,vb,v,dpb[1][u][i],dpb[1][v][j],dpb[1][u][i-j-1]); dpb[1][u][i]=max(dpb[1][u][i],dpb[2][v][j]+dpb[1][u][i-j-1]); } } } else{ //printf("wo shi da hao ren"); for(int i=L;i>=0;i--){ for(int j=0;j<=i-2;j++){ //printf("%d %d %d %d %d %d %d %dhe",u,i,j,vb,v,dpb[1][u][i],dph[v][j],dpb[1][u][i-j-2]); dpb[1][u][i]=max(dpb[1][u][i],dph[v][j]+dpb[1][u][i-j-2]); } } } } for(int i=0;i<=L;i++){ dpb[2][u][i]=max(dpb[1][u][i],dpb[2][u][i]); dpb[1][u][i]=0; } } return; } int main(){ int n; int b; while(scanf("%d",&n)!=EOF){ memset(head,-1,sizeof(head)); cou=0; //printf("%d\n",n); for(int i=1;i<n;i++){ scanf("%d",&b); add(i,b); add(b,i); //printf("%d %d\n",i,b); } scanf("%d",&L); /*for(int i=head[0];i!=-1;i=nextedge[i]){ printf("%d\n",to[i]); }*/ memset(dph,0,sizeof(dph)); memset(dpb,0,sizeof(dpb)); dfs(0,-1); /*for(int i=0;i<n;i++){ for(int j=0;j<=L;j++){ printf("%d ",dpb[2][i][j]); } printf("\n"); } for(int i=0;i<n;i++){ for(int j=0;j<=L;j++){ printf("%d ",dph[i][j]); } printf("\n"); }*/ printf("%d\n",dpb[2][0][L]); } return 0; }