套用KM模板就行了,一道模板题,注意建图就行。
#include<iostream>
#include<cstdlib>
#include<cstdio>
#include<cstring>
#include<algorithm>
#define N 60
using namespace std;
int vx[N],vy[N],lx[N],ly[N],link[N],mat[N][N];
int n;
int dfs(int t)
{
int i;
vx[t]=1;
for(i=1;i<=n;i++)
{
if(vy[i]==0&&lx[t]+ly[i]==mat[t][i])
{
vy[i]=1;
if(link[i]==-1||dfs(link[i]))
{
link[i]=t;
return 1;
}
}
}
return 0;
}
void KM()
{
int i,j,t,k;
memset(lx,0,sizeof(lx));
memset(ly,0,sizeof(ly));
for(i=1; i<=n; i++)
for(j=1; j<=n; j++)
lx[i]=max(lx[i],mat[i][j]);
for(i=1; i<=n; i++)
{
while(1)
{
memset(vx,0,sizeof(vx));
memset(vy,0,sizeof(vy));
if(dfs(i))
break;
else
{
t=9999999;
for(j=1; j<=n; j++)
if(vx[j])
for(k=1; k<=n; k++)
if(vy[k]==0&&lx[j]+ly[k]-mat[j][k]<t)
t=lx[j]+ly[k]-mat[j][k];
for(j=1;j<=n;j++)
{
if(vx[j])
lx[j]-=t;
if(vy[j])
ly[j]+=t;
}
}
}
}
}
int main()
{
int i,j,t,ans,a[N],b[N];
scanf("%d",&t);
int k=0;
while(t--)
{
scanf("%d",&n);
for(i=1; i<=n; i++)
scanf("%d",&a[i]);
for(i=1; i<=n; i++)
scanf("%d",&b[i]);
memset(link,-1,sizeof(link));
memset(mat,0,sizeof(mat));
for(i=1; i<=n; i++)
for(j=1; j<=n; j++)
{
if(a[i]>b[j])
mat[i][j]=2;
if(a[i]==b[j])
mat[i][j]=1;
}
KM();
ans=0;
for(i=1; i<=n; i++)
ans+=mat[link[i]][i];
printf("Case %d: %d\n",++k,ans);
}
return 0;
}