码迷,mamicode.com
首页 > 其他好文 > 详细

二分图匹配(入门篇)

时间:2019-02-01 23:51:20      阅读:394      评论:0      收藏:0      [点我收藏+]

标签:复杂   fine   return   write   png   com   没有   i++   class   

二分图匹配

  • write by BigYellowDog

1. 什么是二分图?

  • 有一个无向图,如果所有的点可以被所有的边分成两个点集。则说这个图为二分图

  • 下图就是一个标准二分图:

技术分享图片

2. 什么是二分图匹配?

  1. 现有一个二分图E,还有它的子集M。如果M中任意一条边都没有公共的端点。则M是一个“匹配”

  2. 如果一个匹配M’中边数是所有匹配中最多的,则说M’为“最大匹配”
  3. 如果匹配M中,所有点都得到了一一匹配,则说M是一个“完全匹配”

技术分享图片

  • 如上图(不用管最下面那一行字)。如果红黑线一起看的画,这个图就是一个二分图。如果只看红线的话,那么其所构成的图就是二分图的一个匹配。同时,它也是一个最大匹配(每个点都得到了一一匹配)。

3. 二分图的实际应用?

  • 举个简单的例子。
  • 一个学校需要分配教学任务,而且要使每科都尽量有老师教,每个老师都尽量有课教。
  • 那么将老师抽象成一个点集,将课程抽象成另一个点集,进行二分图匹配算法,求出最大匹配。

4. 如何实现二分图匹配?

  1. 跑最大流dinic O( \(n\sqrt{m}\) )
  2. 匈牙利算法 O (nm)
  • 那么我这篇文章就只写匈牙利,因为好写且好短。最大流这个坑以后我会填的(逃

  • 噢还有上面那么的复杂度分析n是点数,m是边数

  • 匈牙利算法的流程图解网上大把多好文章。那么我就推荐两个我当时看的吧

  1. 洛谷模版题题解

  2. 匈牙利算法详解

5. 模版题(Luogu P3386)

  • 贴出我的代码,里面有详细注释~
//阅读程序之前,请确保你阅读了我上面推荐的两个文章。
//因为本文视角是以“男女配对”看的(逃
#include <iostream>
#include <cstdio>
#include <cstring>
#define maxn 1005
using namespace std;

int n, m, q, ans;
int rel[maxn][maxn];
int mat[maxn];
bool vis[maxn];

bool dfs(int x)
{
    for(int j = 1; j <= m; j++)
        if(!vis[j] && rel[x][j])
        //如果以前j这个女生跟x这个男生没有联系过并且x这个男生喜欢j这个女生
        {
            vis[j] = 1;
            if(!mat[j] || dfs(mat[j]))
            //如果这个女生没有人跟她配对
            //或者她曾经配对成功的人可以跟另一个人私奔(那么这个女生不就没人配对了嘛)
            {
                mat[j] = x;
                return 1;
            }
        }
    return 0;
}

int main()
{
    cin >> n >> m >> q;
    for(int i = 1; i <= q; i++)
    {
        int u, v;   cin >> u >> v;
        if(v > m || u > n) continue;
        rel[u][v] = 1;
        /*
            * 这里是建单向边。想想我们的配对过程,都是只关注一个点集
            * 相对与另一个点集的情况
        */
    }
    
    for(int i = 1; i <= n; i++)
    {
        //vis数组是标记每个女生是否以前尝试跟i这个男生配对过。
        //如果尝试配对过了,就不用再一次找她了,避免递归进入死循环
        memset(vis, 0, sizeof(vis));
        if(dfs(i)) ans++;
    }
    
    cout << ans;
    return 0;
}

二分图匹配(入门篇)

标签:复杂   fine   return   write   png   com   没有   i++   class   

原文地址:https://www.cnblogs.com/BigYellowDog/p/10347294.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!