//n individual, Match m task, each person completes each task the efficiency is different//start with a matching scheme and now redesign the matching scheme to make the most efficient and save as much as possible//original matching scheme,//*1000 The ownership value, and then for the weight of the original matching edge +1, using km algorithm to find the maximum with the right to match ans//Then the final maximum efficiency is ans/1000, and the number of matching edges retained is Ans%mod#include <iostream>#include <cstdio>#include <cstring>using namespace STD;Const intMAXN = -;Const intMoD = +;Const intINF =0x3f3f3f3f;intMATCH[MAXN], LX[MAXN], LY[MAXN], SLACK[MAXN];intW[MAXN][MAXN], VISX[MAXN], VISY[MAXN];intN, M;BOOLFindintx) {Visx[x] =1; for(inti =1; I <= m;i++) {if(Visy[i])Continue;intTMP = Lx[x] + ly[i]-w[x][i];if(TMP = =0) {Visy[i] =1;if(Match[i] = =-1|| Find (Match[i])) {match[i] = x;return true; } }ElseSlack[i] = min (slack[i], TMP); }return false;}intKM () {memset(Match,-1,sizeof(match)) ;memset(Ly,0,sizeof(ly)) ; for(inti =1; I <= n;i++) {lx[i] =-inf; for(intj =1; J <= m;j++) lx[i] = max (Lx[i], w[i][j]); } for(inti =1; I <= n;i++) { for(intj =1; J <= m;j++) slack[j] = inf; while(1) {memset(VISX,0,sizeof(VISX)) ;memset(Visy,0,sizeof(Visy)) ;if(Find (i)) Break;intd = inf; for(intj =1; J <= m;j++)if(!visy[j]) d = min (d, slack[j]); for(intj =1; J <= n;j++)if(Visx[j]) lx[j]-= D; for(intj =1; J <= m;j++)if(Visy[j]) ly[j] + = D;ElseSLACK[J]-= D; } }intAns =0; for(inti =1; I <= m;i++)if(Match[i]! =-1) ans + = w[match[i]][i];returnAns;}intMain () {//freopen ("In.txt", "R", stdin); while(~scanf("%d%d", &n, &m)) { for(inti =1; I <= n;i++) for(intj =1; J <= m;j++) {scanf("%d", &w[i][j]); W[I][J] *= mod; }intsum =0; for(inti =1; I <= n;i++) {intAscanf("%d", &a); sum + = W[i][a]/mod; w[i][a]++; }intans = KM ();printf("%d%d\n", N-ans%mod, ans/mod-sum); }return 0;}
Copyright NOTICE: This article for Bo Master original article, without Bo Master permission not reproduced.
hdu2853assignment km algorithm