博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
POJ3041 Asteroids(最小点覆盖)
阅读量:7192 次
发布时间:2019-06-29

本文共 1174 字,大约阅读时间需要 3 分钟。

大意:N*N的方格里有K个障碍物(小行星)。我们要清除这些障碍物。对于每一次操作,我们可以清除一行或一列上的障碍物。求最少的操作次数。

建模:把每一行每一列看做一个状态。如果i行j列有一个障碍,就把第i行和第j列连一条边。这样我们的问题就转化成了最小点覆盖(想想为什么,因为每一列或每一行是一个点,我们就要求最少的点使得每一个边(障碍物)被覆盖)

根据König定理,我们知道 最小点覆盖 = 最大匹配,所以就开做了!


#include
#include
#define MAXN 1100#define MAXM 30000struct node{ int v; node *next;}Edge[MAXM*2], *Adj[MAXN*2], *Mcnt = Edge;void Addedge(int u, int v){ node *t = ++Mcnt; t->v = v; t->next = Adj[u]; Adj[u] = t;}int n, m, c[MAXN *2], cnt;bool vis[MAXM];bool dfs(int u){ vis[u] = 1; for(node *p = Adj[u]; p; p = p->next) { if(vis[p->v]) continue; vis[p->v] = 1; if(!c[p->v] || dfs(c[p->v])) { c[u] = p->v; c[p->v] = u; return 1; } } return 0;}int main(){ int a, b; scanf("%d%d", &n, &m); for(int i = 1; i <= m; i ++) { scanf("%d%d", &a, &b); Addedge(a, b + n); } int ans = 0; for(int i = 1; i <= n; i ++) if(!c[i]) { memset(vis, 0, sizeof vis); ans += dfs(i); } printf("%d\n", ans); return 0;}

转载于:https://www.cnblogs.com/geng4512/p/5296941.html

你可能感兴趣的文章
Visual Studio-IIS Express 支持局域网访问配置
查看>>
关于unity里pbr技术和材质 unity5默认shader和传统的对比
查看>>
前端性能监控方案window.performance 调研(转)
查看>>
【转】[FPGA博客大赛](updated)在xilinx的FPGA系统中scanf函数的使用
查看>>
CSS html标签元素分类
查看>>
js调用百度地图接口
查看>>
Oracle 锁表
查看>>
Postman解决Token传参问题
查看>>
BSON的介绍及BSON与JSON的区别
查看>>
BZOJ 1012 单调队列+二分
查看>>
qcow2 修改后端,导致文件系统腐败
查看>>
Simotion 监控问题:Could not add self-signed certificate to certificate store.
查看>>
【codevs2011】最小距离之和 [LNOI2013](Floyd)
查看>>
拥抱函数式编程 I - 基本概念
查看>>
2的正幂末尾数的模式
查看>>
apache官方供下载所有项目所有版本的官方网站地址
查看>>
redis sentinel模式集群
查看>>
从客户端中检测到有潜在危险的 request
查看>>
C# 上传图片前判断上传图片的宽和高
查看>>
Socket.io应用之联网拖拽游戏
查看>>