匈牙利算法是用来求二分图最大匹配的。
所以很关键的一点,跑匈牙利算法的图得是个二分图
最大匹配<=>无增广路径
步骤
对每一个点a,考虑它所有匹配的点b
若是b没有被匹配,则匹配成功
若是b已经被匹配了,则考虑是否能让match[b]换一个匹配对象,可以的话就成功匹配,否则换下一个。
关键语句
!match[j]||find(match[j])
二分图最大匹配难就难到如何看出这是一个二分图最大匹配问题
板子
#include<bits/stdc++.h>
using namespace std;
const int N = 510,M=1e5+5;
int h[N],e[M],ne[M],idx;
int match[N];
bool st[N];
int n1,n2,m;
void add(int a, int b)
{
e[idx] = b, ne[idx] = h[a], h[a] = idx ++ ;
}
bool find(int x)
{
for(int i=h[x];i!=-1;i=ne[i])
{
int j=e[i];
if(!st[j])
{
st[j]=1;
if(!match[j]||find(match[j]))
{
match[j]=x;
return 1;
}
}
}
return 0;
}
int main()
{
scanf("%d%d%d", &n1, &n2, &m);
memset(h, -1, sizeof h);
while(m--)
{
int a,b;
scanf("%d%d",&a,&b);
add(a,b);
}
int res=0;
for(int i=1;i<=n1;i++)
{
memset(st, 0, sizeof st);
if(find(i)) res++;
}
printf("%d\n",res);
return 0;
}