最大二分匹配问题——“相亲巧妙解匈牙利算法”
二分图
1,什么是二分图
二分图又称作二部图,是图论中的一种特殊模型。
设G=(V, E)是一个无向图。如果顶点集 V可分割为两个互不相交的子集X和Y,并且图中每条边连接的两个顶点一个在 X中,另一个在 Y中,则称图G为二分图。

2,二分图相关性质
定理:当且仅当无向图G的每一个环
的结点数均是偶数时,图G才是一个二分图。如果无环,也视为二分图。
3,二分图的判定
如果一个图是连通的,可以用如下的染色法判定是否二分图:
我们把X部的结点颜色设为0,Y部的颜色设为1。
从某个未染色的结点u开始,做BFS或者DFS 。把u染为0,枚举u的儿子v。如果v未染色,就染为与u相反的颜色,如果已染色,则判断u与v的颜色是否相同,相同则不是二分图。
如果一个图不连通,则在每个连通块中作判定。如图所示

二分图的判定结合这道模板题看下:
给定一个 n 个点 m 条边的无向图,图中可能存在重边和自环。
请你判断这个图是否是二分图。
输入格式
第一行包含两个整数 n 和 m。
接下来 m 行,每行包含两个整数 u 和 v,表示点 u 和点 v 之间存在一条边。
输出格式
如果给定图是二分图,则输出 Yes,否则输出 No。
数据范围
1≤n,m≤105
输入样例:
4 4
1 3
1 4
2 3
2 4
输出样例:
Yes
题目来源:染色法判断二分图
推荐 这道题的题中相关解释是根据我后面将的“男女相亲”来陈述的,可以先去看看男女相亲巧解匈牙利
#include<cstring>
#include<iostream>
using namespace std;
const int N = 100010, M = 200010;
int n, m;
int h[N], e[M], ne[M], idex;//因为邻接表存的是无向图,不仅要存ab也要存ba所以M的范围是N的两倍
int st[N];//判断点是否染色以及染的颜色是否相同
void add(int x, int y)
{
//表示的是x->y的边
e[idex] = y;
ne[idex] = h[x];
h[x] = idex++;
}
bool dfs(int u, int c)//表示将点u染成颜色c
{
st[u] = c;
for (int i = h[u]; i != -1; i = ne[i])
{
int j = e[i];
if (!st[j])//如果未染色
{
if (!dfs(j, 3 - c))
return false;
}
else if (st[j] == c) return false;//如果染色但是染色相同那么也是没用的
}
return true;
}
int main()
{
cin >> n >> m;
memset(h, -1, sizeof h);
while (m--)
{
int u, v;
cin >> u >> v;
add(u, v

本文探讨了二分图的概念、判定方法,以及其在最大匹配问题中的应用,通过实例说明如何利用匈牙利算法解决男女相亲中的配对问题。同时,通过编程实例展示了如何在实际场景中使用匈牙利算法求解最小点覆盖,揭示了最大匹配和最小点覆盖之间的König定理。
最低0.47元/天 解锁文章
1236





