1. 程式人生 > >hdu2415(樹上背包)

hdu2415(樹上背包)

esp turn stream log 字符串處理 oid == clu memset

這道題好像沒什麽人寫題解,於是寫了一發

題意:有個壞蛋想要參加競選,需要得到m個人的支持,買通第i個人(1<=i<=n)需要一個cost[i],同時這些人又有上下屬關系,只要買通了領導,他的下屬(可以是下屬的下屬)也會給你投票,問最少要花多少錢

數據範圍:N<=200,m<=n;

其實就是比較裸的樹上分組背包,每個子節點的背包是一個組,選自己也是一個組,dfs搞一搞就好了,然而字符串處理實在惡心.....

#include<string>
#include<cstring>
#include<iostream>
#include<algorithm>
#include
<cstdio> #include<cmath> #include<vector> #include<map> #include<queue> using namespace std; const int MAX=1<<29; int n,m; map<string,int>dui; vector<int>arr[205]; char str[100005],tmp[105]; int dp[205][205],fa[205],siz[205],cost[205],cnt=0; void dfs1(int now) {
int i,j; siz[now]=1; for(i=0;i<arr[now].size();i++) { int v=arr[now][i]; dfs1(v); siz[now]+=siz[v]; } } void dfs(int now) { int i,j,k; for(i=0;i<arr[now].size();i++) { dfs(arr[now][i]); int v=arr[now][i]; for(j=m;j>=1
;j--)for(k=1;k<=j;k++)dp[now][j]=min(dp[now][j],dp[now][j-k]+dp[v][k]); } if(now!=n+1)for(i=1;i<=min(m,siz[now]);i++)dp[now][i]=min(cost[now],dp[now][i]); return ; } int main() { int i,j; char ss[10]; while(scanf("%s",ss)!=EOF) { n=0; cnt=0; if(ss[0]==#)return 0; for(i=0;i<strlen(ss);i++)n*=10,n+=ss[i]-0; scanf("%d",&m); int i,j; for(i=0;i<=n+1;i++)arr[i].clear(); dui.clear(); getchar(); for(i=1;i<=n+1;i++)fa[i]=i; for(i=0;i<n;i++) { gets(str); int len=strlen(str); for(j=0;j<len;j++)if(str[j]== )break; int pos=j; memset(tmp,0,sizeof(tmp)); for(j=0;j<pos;j++)tmp[j]=str[j]; string a=tmp; if(!dui[a])dui[a]=++cnt; int name1=dui[a],costs=0; while(str[pos]>9||str[pos]<0)pos++; for(j=pos;;j++) { if(str[j]==\0||str[j]>9||str[j]<0) { pos=j; break; } costs*=10; costs+=str[j]-0; } cost[name1]=costs; int nums=0; string b; for(j=pos+1;j<len;j++) { if(str[j]!= ) { tmp[nums++]=str[j]; if(str[j+1]== ||str[j+1]==\0) { tmp[nums++]=\0; b=tmp; nums=0; if(!dui[b])dui[b]=++cnt; int name2=dui[b]; arr[name1].push_back(name2); fa[name2]=name1; } } } } for(i=1;i<=n+1;i++) { dp[i][0]=0; for(j=1;j<=m;j++)dp[i][j]=MAX; } for(i=1;i<=n;i++)if(fa[i]==i)arr[n+1].push_back(i); dfs1(n+1); dfs(n+1); printf("%d\n",dp[n+1][m]); } } /* 9 5 A 45 B C B 20 C 30 D 60 E F E 20 F 50 G H G 10 H 25 I I 15 */

hdu2415(樹上背包)