题目大意:在一个n*m的网格中,有k个目标,现在可以任选一行或列消除在其上的所有目标,求出最少选择次数及选法. 题目分析:经典的最小点覆盖问题,并且输出一个最小点覆盖集.在求出最大匹配之后,以未覆盖的x点进行标记,沿着未覆盖->覆盖->未覆盖->覆盖...的路径标记,最后x中未标记的和y中标记的点构成最小点覆盖集. 代码如下: # include<iostream> # include<cstdio> # include<cstring> # incl…
题目链接:http://acm.hust.edu.cn/vjudge/problem/viewProblem.action?id=27475 [思路] 二分图的最小点覆盖以及构造最小覆盖. 二分图的最小点覆盖即在二分图中选出最少的点使能够将所有的边覆盖.构造思路是从所有未盖点出发拓展匈牙利树,X中的未标记点与Y中的已标记点为最小覆盖集. 具体可见:http://www.tuicool.com/articles/jmAnEb [代码] #include<cstdio> #include<c…
题意:给一个r*c的矩阵,某些格子中可能有一些怪物,可以在一行或一列防止一枚大炮,大炮会扫光整行/列的怪,问最少需要多少炮?输出炮的位置. 思路: 先每行和列都放一个炮,把炮当成点,把怪当成边,一边连接行炮,另一边是列炮,只要其中任何一个扫了,另一个就不必了.所以明显是求最小点覆盖,用最少的点(即炮)覆盖最多的边(即怪).进而转成最大匹配.因 最大匹配数=最小覆盖数. 这题还得求炮的位置,也就是覆盖点集.可以根据匈牙利数来构造,而且可以用同匈牙利算法那个DFS函数,稍微加点东西而已.神奇之处在于…
题目链接:https://vjudge.net/problem/UVA-11419 题解: 1.二分图匹配之最小点覆盖.:把x坐标和y坐标看成是点, 图中的目标看成是边,所以最终的目的是求出用最少的点,去覆盖掉所有的边.如果在M[x][y]处有目标,则连一条边x-y.接着跑一遍匈牙利算法. 2.除此之外,题目还要求输出最小覆盖点集.可知我们已经求出了最大匹配数,首先我们把所有的覆盖点都落在左边的匹配点上.但是这样做却不能保证所有的边都会被覆盖,因为假设左边有未匹配点,且这些未匹配点与右边的点(是…
题意:在方格图上打小怪,每次可以清除一整行或一整列的小怪,问最少的步数是多少,又应该在哪些位置操作(对输出顺序没有要求). 分析:最小覆盖问题 这是一种在方格图上建立的模型:令S集表示“行”,T集表示“列”,那么小怪站的位置w(i,j),就是二分图上的边.如此建图,那么每次清除,就是把与某个点相连的边全部清除,问最少选择多少个点.(这也是最小点覆盖的概念:选择尽量少的点,使得每条边至少有一个端点被选中) 这里有一个König定理:最大二分匹配数==最小覆盖点数. 既然是求最小点覆盖,那么自然是选…
https://vjudge.net/problem/UVA-11419 题意:一个网格里面有一些目标,可以从某一行,某一列发射一发子弹,可以打掉它:求最少的子弹,和在哪里打? 思路: 每个点的x坐标与y坐标相连,现在就是要找一个最小点覆盖,同时还要输出哪些点被覆盖了. #include <cstdio> #include <cstring> #include <vector> #include <algorithm> using namespace std…
前言 博主很笨 ,如有纰漏,欢迎在评论区指出讨论. 二分图的最大匹配使用 \(Dinic\) 算法进行实现,时间复杂度为 \(O(n\sqrt{e})\),其中, \(n\)为二分图中左部点的数量, \(e\) 为二分图中的边数.若是匈牙利算法,时间复杂度为 \(O(nm)\) , \(m\) 为二分图中右部点的数量,不建议使用. 文章中的例题链接. König定理 定理内容:二分图最小点覆盖的点的数量等于二分图最大匹配的边的数量. 构造方法 \(+\) 简单证明: 首先求出二分图中的最大匹配,…
UVA11419 SAM I AM 给定一个 \(R\times C\) 的矩阵中的 \(N\) 个点,求最少选取多少个行或列才能使得每个给出的点都被一行或一列覆盖,输出方案 \(R,\ C\leq10^3,\ N\leq10^6\) 网络流 易知原题即为建出二分图后跑最小点覆盖求方案 这里只是记录一下如何求方案-- 找出从原点开始,只经过没被使用的边,构成的连通块 如果左侧节点没被包含在连通块中,输出方案 如果右侧节点被包含在连通块中,输出方案 代码 #include <bits/stdc++…
子问题定义: 对于图中的每个结点,有两种状态,即属于最小点覆盖和不属于最小点覆盖,定义minSet[i][0]表示结点i属于点覆盖,并且以i为根的树的最小点覆盖的大小.minSet[i][1]表示点i不属于点覆盖,并且以i为根的树的最小点覆盖的大小. 递归关系: 对于minSet[i][0],i的孩子结点可以属于点覆盖,也可以不属于点覆盖,取其使以i为根的子树的点覆盖最小的情况,因此 对于minSet[i][1],由于i不属于点覆盖,因此其所有孩子结点都必须属于点覆盖,因此 初值设定: minS…
//匈牙利算法-DFS //求最小点覆盖集 == 求最大匹配 //Time:0Ms Memory:208K #include<iostream> #include<cstring> #include<cstdio> #include<algorithm> using namespace std; #define MAX 105 #define INF 0x3f3f3f3f int n,m,k; int gp[MAX][MAX]; bool sx[MAX],s…