二分图前期基础之增广路

二分图前期基础之增广路二分图前期基础之增广路刚开始学习的时候 总是受困于增广路径 不明白增广路径是如何应用以及其具体的含义是什么 感谢博客 https www cnblogs com logosG p logos html 为了充分表达敬意 放在了文首 QAQ 晕了几天总算是明白了 总算是明白 KM 算法的神奇之处了一 匈牙利算法匈牙利算法用于解决什么问题 匈牙利算法用于解决二分图的最大匹配问题 什么是二分图

二分图前期基础之增广路

     刚开始学习的时候,总是受困于增广路径,不明白增广路径是如何应用以及其具体的含义是什么,感谢博客https://www.cnblogs.com/logosG/p/logos.html 为了充分表达敬意,放在了文首 QAQ 晕了几天总算是明白了,总算是明白KM算法的神奇之处了

一、匈牙利算法

匈牙利算法用于解决什么问题?

匈牙利算法用于解决二分图的最大匹配问题。

什么是二分图?我们不妨来考虑这样一个问题,在一家公司里,有员工A,B,C,有三种工作a,b,c,如果员工和工作之间有线相连,则代表员工能胜任这份工作。

figure1.1

如图所示,员工A能胜任a,c工作,员工B能胜任a,b,c工作,而员工C只能胜任c工作。

上图就是所谓的“二分图”(请忽略图中箭头),简单的说,上图可划分为两个集合{员工},{工作},两个集合之间的元素可以相连,同一个集合内的元素不能相连。

下面请解决这样一个问题:请给出一个方案,让尽可能多的员工有不同的工作做。“匈牙利算法”的出现就是为了解决这个问题。

下面给出这个问题的解决方案:(读者看到这里可能会想,解决这个问题不是很简单吗?A→a,B→b,C→c不就好了?请注意:任何算法的给出都是为了规整化一个问题的解决步骤,其目的是为了在问题规模越来越大时算法对其仍然适用,如果公司有10个员工或者更多,读者想必不能一眼看出答案,此时,算法的作用便体现出来了。)

我们先帮A找工作做,不妨先帮A连上a(红线表示此时两者已经匹配),表示A去做a工作。

二分图前期基础之增广路

  

接下来我们帮B找工作做,B的第一条线跟a相连,B也想做工作a。

二分图前期基础之增广路

这时候就发生了冲突(collision),如何解决呢?

匈牙利算法”指出 通过一条增广路径,通过取反操作,我们就能匹配更多的点。

什么是增广路径?增广路径是指,由一个未匹配的顶点开始,经过若干个匹配顶点,最后到达对面集合的一个未匹配顶点的路径,即这条路径将两个不同集合的两个未匹配顶点通过一系列匹配顶点相连。

比如此题中,B想做工作a,于是A想着换一个工作,我们连上A,c。

二分图前期基础之增广路

如图,B→aA→c 其中B,c未匹配,A,a已匹配,按照定义,这就是一条增广路径,我们对其进行取反操作,就变成了下图。

二分图前期基础之增广路

取反操作为我们带来了什么?原本只有一边匹配,现在有两边匹配了,而且冲突也解决了,这就是匈牙利算法的妙处,我们能通过不停的寻找这样一条增广路径,从而找到二分图的最大匹配

下面我们继续寻找增广路径。

二分图前期基础之增广路

二分图前期基础之增广路

二分图前期基础之增广路

二分图前期基础之增广路

最终,我们得到了一个最大匹配:A匹配a,B匹配b,C匹配c,就算集合中的元素很多很多,我们仍能通过匈牙利算法得到该二分图的最大匹配。

二、KM算法

二分图前期基础之增广路

这种问题被称为带权二分图的最优匹配问题,可由KM算法解决。

比如上图,A做工作a的效率为3,做工作c的效率为4……以此类推。

不了解KM算法的人如何解决这个问题?我们只需要用匈牙利算法找到所有的最大匹配,比较每个最大匹配的权重,再选出最大权重的最优匹配即可。这不失为一个解决方案,但是,如果公司员工的数量越来越多,此种算法的实行难度也就越来越大,我们必须另辟蹊径:KM算法。

KM算法解决此题的步骤如下所示:

1.首先对每个顶点赋值,将左边的顶点赋值为最大权重,右边的顶点赋值为0。

如图,我们将顶点A赋值为其两边中较大的4。

二分图前期基础之增广路

2.进行匹配,我们匹配的原则是:只与权重相同的边匹配,若是找不到边匹配,对此条路径的所有左边顶点-1,右边顶点+1,再进行匹配,若还是匹配不到,重复+1和-1操作。(这里看不懂可以跳过,直接看下面的操作,之后再回头来看这里。)

对A进行匹配,符合匹配条件的边只有Ac边。

匹配成功!

二分图前期基础之增广路

接下来我们对B进行匹配,顶点B值为3,Bc边权重为3,匹配成~ 等等,A已经匹配c了,发生了冲突,怎么办?我们这时候第一时间应该想到的是,让B换个工作,但根据匹配原则,只有Bc边 3+0=0 满足要求,于是B不能换边了,那A能不能换边呢?对A来说,也是只有Ac边满足4+0=4的要求,于是A也不能换边,走投无路了,怎么办?

二分图前期基础之增广路

从常识的角度思考:其实我们寻找最优匹配的过程,也就是帮每个员工找到他们工作效率最高的工作,但是,有些工作会冲突,比如现在,B员工和A员工工作c的效率都是最高,这时我们应该让A或者B换一份工作,但是这时候换工作的话我们只能换到降低总体效率值的工作,也就是说,如果令R=左边顶点所有值相加,若发生了冲突,则最终工作效率一定小于R,但是,我们现在只要求最优匹配,所以,如果A换一份工作降低的工作效率比较少的话,我们是能接受的(对B同样如此)。

在KM算法中如何体现呢?

现在参与到这个冲突的顶点是A,B和c,令所有左边顶点值-1,右边顶点值+1,即 A-1,B-1. c+1,结果如下图所示。

二分图前期基础之增广路

我们进行了上述操作后会发现,若是左边有n个顶点参与运算,则右边就有n-1个顶点参与运算,整体效率值下降了1*(n-(n-1))=1,而对于A来说,Ac本来为可匹配的边,现在仍为可匹配边(3+1=4),对于B来说,Bc本来为可匹配的边,现在仍为可匹配的边(2+1=4),我们通过上述操作,为A增加了一条可匹配的边Aa,为B增加了一条可匹配的边Ba。

现在我们再来匹配,对B来说,Ba边 2+0=2,满足条件,所以B换边,a现在为未匹配状态,Ba匹配!

二分图前期基础之增广路

我们现在匹配最后一条边C,Cc 5+1!=5,C边无边能匹配,所以C-1。

二分图前期基础之增广路

现在Cc边 4+1=5,可以匹配,但是c已匹配了,发生冲突,C此时不能换边,于是便去找A,对于A来说,Aa此时也为可匹配边,但是a已匹配,A又去找B。

二分图前期基础之增广路

  

二分图前期基础之增广路

B现在无边可以匹配了,2+0!=1 ,现在的路径是C→c→A→a→B,所以A-1,B-1,C-1,a+1,c+1。如下图所示。

二分图前期基础之增广路

对于B来说,现在Bb 1+0=1 可匹配!

二分图前期基础之增广路

使用匈牙利算法,对此条路径上的边取反。

二分图前期基础之增广路

如图,便完成了此题的最优匹配。

读者可以发现,这题中冲突一共发生了3次,所以我们一共降低了3次效率值,但是我们每次降低的效率值都是最少的,所以我们完成的仍然是最优匹配

这就是KM算法的整个过程,整体思路就是:每次都帮一个顶点匹配最大权重边,利用匈牙利算法完成最大匹配,最终我们完成的就是最优匹配

PS:笔者此文旨在用通俗易懂的语言解释匈牙利算法和KM算法,所以对部分定理未加以证明,甚至有的部分一笔带过,这是为了全文的流畅性考虑,不专业之处请多多谅解。

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/233491.html原文链接:https://javaforall.net

(0)
全栈程序员-站长的头像全栈程序员-站长


相关推荐

  • python zipfile_Python 学习入门(16)—— zipfile

    python zipfile_Python 学习入门(16)—— zipfilezipfile是python里用来做zip格式编码的压缩和解压缩的,由于是很常见的zip格式,所以这个模块使用频率也是比较高。zipfile里有两个非常重要的class,分别是ZipFile和ZipInfo,在绝大多数的情况下,只需要使用这两个class就可以。1)ZipFile是主要的类,用来创建和读取zip文件;2)ZipInfo是存储的zip文件的每个文件的信息的。1)简单应用如果你仅…

    2022年9月17日
    3
  • 元素守恒计算方法_树状数组求逆序对

    元素守恒计算方法_树状数组求逆序对给定一个整数数组 nums,按要求返回一个新数组 counts。数组 counts 有该性质: counts[i] 的值是 nums[i] 右侧小于 nums[i] 的元素的数量。示例:输入:nums = [5,2,6,1]输出:[2,1,1,0] 解释:5 的右侧有 2 个更小的元素 (2 和 1)2 的右侧仅有 1 个更小的元素 (1)6 的右侧有 1 个更小的元素 (1)1 的右侧有 0 个更小的元素提示:0 <= nums.length <= 10^5-10^4

    2022年8月9日
    7
  • 英语单词记忆法拆分2000个_什么是hash算法

    英语单词记忆法拆分2000个_什么是hash算法给定一个非空字符串 s 和一个包含非空单词列表的字典 wordDict,在字符串中增加空格来构建一个句子,使得句子中所有的单词都在词典中。返回所有这些可能的句子。说明:分隔时可以重复使用字典中的单词。你可以假设字典中没有重复的单词。示例 1:输入:s = “catsanddog”wordDict = [“cat”, “cats”, “and”, “sand”, “dog”]输出:[ “cats and dog”, “cat sand dog”]示例 2:输入:s = “

    2022年8月9日
    7
  • 如何简化美化LEfSe分析结果中的Cladogram图

    如何简化美化LEfSe分析结果中的Cladogram图文章目录如何简化美化LEfSe分析结果中的Cladogram图写在前面美颜攻略扩展阅读Reference猜你喜欢写在后面如何简化美化LEfSe分析结果中的Cladogram图作者:赵维中国科学院天津工业生物技术研究所审稿:刘永鑫中国科学院遗传与发育生物学研究所写在前面关于LEfSe分析,相信大家早已耳熟能详。网上也有很多指导如何做LEfSe分析流程的文章。可是在实际应用中,仍然会遇到…

    2022年6月9日
    50
  • 五、Abp vNext 基础篇丨博客聚合功能

    五、Abp vNext 基础篇丨博客聚合功能介绍业务篇章先从客户端开始写,另外补充一下我给项目起名的时候没多想起的太随意了,结果后面有些地方命名冲突了需要通过手动using不过问题不大。开工应用层根据第三章分层架构里面讲到的现在我们模型

    2022年7月4日
    23
  • 迭代器Python_python迭代器使用

    迭代器Python_python迭代器使用迭代器迭代是访问集合元素的一种方式。迭代器是一个可以记住遍历的位置的对象。迭代器对象从集合的第一个元素开始访问,直到所有的元素被访问完结束。迭代器只能往前不会后退。可迭代对象我们已经知道可以对l

    2022年8月6日
    8

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号