直接套KM模板。
#include <cmath>
#include <cstdio>
#include <cstring>
#include <iostream>
#define MAXN 2147483647;
using namespace std;
int n,ly[501],lx[501],slack[501],fy[501],w[501][501];
bool mx[501],my[501];
int find(int x)
{
mx[x]=true;
for(int i=1;i <= n;i++)
if(!my[i])
{
int a=lx[x]+ly[i]-w[x][i];
if(a == 0)
{
my[i]=true;
if(!fy[i] || find(fy[i]))
{
fy[i]=x;
return true;
}
}
else slack[i]=min(slack[i],a);
}
return false;
}
void km()
{
memset(lx,0,sizeof(lx));
memset(ly,0,sizeof(ly));
memset(fy,0,sizeof(fy));
for(int i=1;i <= n;i++)
for(int j=1;j <= n;j++)
lx[i]=max(lx[i],w[i][j]);
for(int i=1;i <= n;i++)
{
for(int j=1;j <= n;j++)
slack[j]=MAXN;
while(true)
{
memset(mx,0,sizeof(mx));
memset(my,0,sizeof(my));
if(find(i)) break;
int a=MAXN;
for(int j=1;j <= n;j++)
if(!my[j]) a=min(a,slack[j]);
for(int j=1;j <= n;j++)
if(mx[j]) lx[j]-=a;
for(int j=1;j <= n;j++)
if(my[j])
{
ly[j]+=a;
}
else slack[j]-=a;
}
}
}
int main()
{
ios::sync_with_stdio(false);
while(cin>>n)
{
for(int i=1;i <= n;i++)
for(int j=1;j <= n;j++)
cin>>w[i][j];
km();
int ans=0;
for(int i=1;i <= n;i++)
{
cout<<lx[i]<<" ";
ans+=lx[i];
}
cout<<endl;
for(int i=1;i <= n;i++)
{
cout<<ly[i]<<" ";
ans+=ly[i];
}
cout<<endl;
cout<<ans<<endl;
}
}