1. 程式人生 > 實用技巧 >二分圖匹配

二分圖匹配

簡介

如果在當前匹配方案下再也找不到增廣路,那麼當前匹配就是最大匹配了。

流程

  1. 從任意一個沒有被配對的點\(x\)開始,從點\(x\)的邊中任意選一條邊。如果此時點\(i\)沒有被配對那麼配對成功,則找到了一條增廣路。如果點\(i\)此時已經被配對了,那麼可以嘗試將點\(i\)與其他點配對。如果嘗試成功,則找到一條增廣路。這裡用\(match\)來記錄配對關係,即\(match_i=x\)。並且將配對數\(+1\)。這個過程我們用dfs來實現。

  2. 如果配對失敗,就從點\(x\)的邊中重選一條邊嘗試。直到點\(x\)配對成功或嘗試完x所有的邊。

  3. 接下來對沒有配對的點一一進行配對,直到所有的點都嘗試完畢找不到新的增廣路。

程式碼

#include<bits/stdc++.h>
using namespace std;
const int N=1005;
int n,m,e,ans,match[N];
bool a[N][N],vis[N];
bool dfs(int x) {
	for(int i=1; i<=m; i++) {
		if(!vis[i]&&a[x][i]) {
			vis[i]=1;
			if(!match[i]||dfs(match[i])) {
				match[i]=x;
				return 1;
			}
		}
	}
	return 0;
}
int main() {
	scanf("%d %d %d",&n,&m,&e);
	for(int i=1,u,v; i<=e; i++) {
		scanf("%d %d",&u,&v),a[u][v]=1;
	}
	for (int i=1; i<=n; i++){
        ans+=dfs(i);
        memset(vis,0,sizeof(vis));
    }
    printf("%d",ans);
	return 0;
}

後記

這裡轉載。