二分图匹配(匈牙利算法模板)
二分最大匹配的匈牙利算法模板
/* *************************************************** 二分图匹配(匈牙利算法的DFS实现) INIT:G[][]两边定点划分的情况 CALL:res=Hungary();输出最大匹配数 优点:适于稠密图,DFS找增广路快,实现简洁易于理解 时间复杂度:O(VE); *************************************************** */ const int MAXN = 510; int uN,vN;//u,v数目 int G[MAXN][MAXN];//编号是1~n的 int linker[MAXN]; bool used[MAXN]; bool dfs(int u) { int v; for(v=1;v<=vN;v++){ if(G[u][v]&&!used[v]){ used[v]=true; if(linker[v]==-1||dfs(linker[v])){ linker[v]=u; return true; } } } return false; } int Hungary() { int res=0; int u; memset(linker,-1,sizeof(linker)); for(u=1;u<=uN;u++){ memset(used,false,sizeof(used)); if(dfs(u)) res++; } return res; }
例题:HDU 2063 过山车 (模板题)
#include<stdio.h> #include<string.h> #include<iostream> using namespace std; /* *************************************************** 二分图匹配(匈牙利算法的DFS实现) INIT:G[][]两边定点划分的情况 CALL:res=Hungary();输出最大匹配数 优点:适于稠密图,DFS找增广路快,实现简洁易于理解 时间复杂度:O(VE); *************************************************** */ const int MAXN = 510; int uN,vN;//u,v数目 int G[MAXN][MAXN];//编号是1~n的 int linker[MAXN]; bool used[MAXN]; bool dfs(int u) { int v; for(v=1;v<=vN;v++){ if(G[u][v]&&!used[v]){ used[v]=true; if(linker[v]==-1||dfs(linker[v])){ linker[v]=u; return true; } } } return false; } int Hungary() { int res=0; int u; memset(linker,-1,sizeof(linker)); for(u=1;u<=uN;u++){ memset(used,false,sizeof(used)); if(dfs(u)) res++; } return res; } int main() { int k; while(scanf("%d",&k)==1&&k){ scanf("%d%d",&uN,&vN); memset(G,0,sizeof(G)); for(int i=1;i<=k;i++){ int u,v; scanf("%d%d",&u,&v); G[u][v]=1; } printf("%d\n",Hungary()); } return 0; }