struct Hungary {
int n, m; // 两个集合点的个数
int vis[maxn], link[maxn];
vector <int> edge[maxn];
void init(int n, int m)
{
this -> n = n;
this -> m = m;
memset(link, -1, sizeof(link));
for(int i = 0;i <= n + m;i ++)
edge[i].clear();
}
void addEdge(int s, int t)
{
edge[s].push_back(t);
edge[t].push_back(s);
}
int find(int k)
{
for(int i = 0;i < edge[k].size();i ++)
{
int t = edge[k][i];
if(vis[t] == 0)
{
vis[t] = 1;
if(link[t] == -1 || find(link[t]))
{
link[t] = k;
return 1;
}
}
}
return 0;
}
int maxmatch()
{
int ans = 0;
for(int i = 1;i <= n;i ++)
{
memset(vis, 0, sizeof(vis));
if(find(i)) ans ++;
}
return ans;
}
}Match;
附上矩阵版本
struct Hungary {
int n, m;
int mp[500][500];
int link[maxn], vis[maxn];
void init(int n, int m)
{
this -> n = n;
this -> m = m;
memset(link, -1, sizeof(link));
memset(mp, 0, sizeof(mp));
}
void addEdge(int s, int t)
{
mp[s][t] = 1; // 根据题目需要可以改有向或无向
}
int find(int k)
{
for(int i = 1;i <= m;i ++)
{
if(mp[k][i] && vis[i] == 0)
{
vis[i] = 1;
if(link[i] == -1 || find(link[i]))
{
link[i] = k;
return 1;
}
}
}
return 0;
}
int maxmatch()
{
int ans = 0;
for(int i = 1;i <= n;i ++)
{
memset(vis, 0, sizeof(vis));
if(find(i)) ans ++;
}
return ans;
}
}Match;