hdu 2255 奔小康赚大钱 KM算法
看到这么奇葩的题目名我笑了,后来这么一个裸的KM调了2小时我哭了……
这是个裸的KM算法,也没什么多说的,主要是注意多组数据时,每次都要把各种数组清空啊,赋值啊什么的,反正比较麻烦。至于为什么调了2小时,在修改标号的时候我修改的是vx和vy……
1 #include <cstdio> 2 #include <cstring> 3 #include <cstdlib> 4 #define N 310 5 #define inf 0xff 6 int a[N][N]={0},n,px[N],py[N],vx[N],vy[N],str[N],fa[N]; 7 int find(int now) 8 { 9 int i; 10 if (now==0) 11 return 1; 12 vx[now]=1; 13 for (i=1;i<=n;i++) 14 if (a[now][i]==px[now]+py[i]&&!vy[i]) 15 { 16 vy[i]=1; 17 if (fa[i]==0||find(fa[i])) 18 { 19 fa[i]=now; 20 return 1; 21 } 22 } 23 else 24 if (px[now]+py[i]-a[now][i]<str[i]) 25 str[i]=px[now]+py[i]-a[now][i]; 26 return 0; 27 } 28 int KM() 29 { 30 int i,j,k,x,y,z; 31 for (i=1;i<=n;i++) 32 { 33 for (j=1;j<=n;j++) 34 str[j]=inf; 35 while (1) 36 { 37 memset(vx,0,sizeof(vx)); 38 memset(vy,0,sizeof(vy)); 39 if (find(i)) 40 break; 41 k=inf; 42 for (x=1;x<=n;x++) 43 if (!vy[x]&&k>str[x]) 44 k=str[x]; 45 for (x=1;x<=n;x++) 46 { 47 if (vx[x]) 48 px[x]-=k; 49 if (vy[x]) 50 py[x]+=k; 51 else 52 str[x]-=k; 53 } 54 } 55 } 56 z=0; 57 for (i=1;i<=n;i++) 58 z+=a[fa[i]][i]; 59 return z; 60 } 61 int main() 62 { 63 int i,j,k,x,y,z; 64 while(scanf("%d",&n)!=EOF) 65 { 66 memset(px,0,sizeof(px)); 67 memset(py,0,sizeof(py)); 68 memset(fa,0,sizeof(fa)); 69 for (i=1;i<=n;i++) 70 for (j=1;j<=n;j++) 71 { 72 scanf("%d",&x); 73 a[i][j]=x; 74 if (x>px[i]) 75 px[i]=x; 76 } 77 printf("%d\n",KM()); 78 } 79 }