POJ1637 Sightseeing tour(判定混合图欧拉回路)
有向连通图存在欧拉回路的充要条件是所有点入度=出度。
首先随便给定所有无向边一个方向(不妨直接是u->v方向),记录所有点的度(记:度=入度-出度)。
这时如果有点的度不等于0,那么就不存在欧拉回路,就需要改变那些无向边的方向。
而改变一个无向边的方向,相当于边上两个端点的入度和出度都变化了1,它们的度±2。
另外,这样可以证明如果这时某个点的度为奇数那么一定不存在存在欧拉回路的解。
构图如下:所有无向边(u,v),建立容量为1的(u,v)边;所有度小于0的点u,建立容量为-deg/2的(vs,u)边;所有度大于0的点u,建立容量为deg/2(u,vt)边。
最后如果和vs、vt关联的边都满流,那么就有存在欧拉回路的解。
1 #include<cstdio> 2 #include<cstring> 3 #include<queue> 4 #include<algorithm> 5 using namespace std; 6 #define INF (1<<30) 7 #define MAXN 222 8 #define MAXM 4444 9 10 struct Edge{ 11 int v,cap,flow,next; 12 }edge[MAXM]; 13 int vs,vt,NE,NV; 14 int head[MAXN]; 15 16 void addEdge(int u,int v,int cap){ 17 edge[NE].v=v; edge[NE].cap=cap; edge[NE].flow=0; 18 edge[NE].next=head[u]; head[u]=NE++; 19 edge[NE].v=u; edge[NE].cap=0; edge[NE].flow=0; 20 edge[NE].next=head[v]; head[v]=NE++; 21 } 22 23 int level[MAXN]; 24 int gap[MAXN]; 25 void bfs(){ 26 memset(level,-1,sizeof(level)); 27 memset(gap,0,sizeof(gap)); 28 level[vt]=0; 29 gap[level[vt]]++; 30 queue<int> que; 31 que.push(vt); 32 while(!que.empty()){ 33 int u=que.front(); que.pop(); 34 for(int i=head[u]; i!=-1; i=edge[i].next){ 35 int v=edge[i].v; 36 if(level[v]!=-1) continue; 37 level[v]=level[u]+1; 38 gap[level[v]]++; 39 que.push(v); 40 } 41 } 42 } 43 44 int pre[MAXN]; 45 int cur[MAXN]; 46 int ISAP(){ 47 bfs(); 48 memset(pre,-1,sizeof(pre)); 49 memcpy(cur,head,sizeof(head)); 50 int u=pre[vs]=vs,flow=0,aug=INF; 51 gap[0]=NV; 52 while(level[vs]<NV){ 53 bool flag=false; 54 for(int &i=cur[u]; i!=-1; i=edge[i].next){ 55 int v=edge[i].v; 56 if(edge[i].cap!=edge[i].flow && level[u]==level[v]+1){ 57 flag=true; 58 pre[v]=u; 59 u=v; 60 //aug=(aug==-1?edge[i].cap:min(aug,edge[i].cap)); 61 aug=min(aug,edge[i].cap-edge[i].flow); 62 if(v==vt){ 63 flow+=aug; 64 for(u=pre[v]; v!=vs; v=u,u=pre[u]){ 65 edge[cur[u]].flow+=aug; 66 edge[cur[u]^1].flow-=aug; 67 } 68 //aug=-1; 69 aug=INF; 70 } 71 break; 72 } 73 } 74 if(flag) continue; 75 int minlevel=NV; 76 for(int i=head[u]; i!=-1; i=edge[i].next){ 77 int v=edge[i].v; 78 if(edge[i].cap!=edge[i].flow && level[v]<minlevel){ 79 minlevel=level[v]; 80 cur[u]=i; 81 } 82 } 83 if(--gap[level[u]]==0) break; 84 level[u]=minlevel+1; 85 gap[level[u]]++; 86 u=pre[u]; 87 } 88 return flow; 89 } 90 91 int n,m,deg[MAXN]; 92 bool solve(){ 93 for(int i=1; i<=n; ++i){ 94 if(abs(deg[i])&1) return 0; 95 if(deg[i]>0) addEdge(i,vt,deg[i]>>1); 96 else if(deg[i]<0) addEdge(vs,i,(-deg[i])>>1); 97 } 98 ISAP(); 99 for(int i=0; i<NE ;i+=2){ 100 if(edge[i^1].v!=vs&&edge[i].v!=vt) continue; 101 if(edge[i].cap!=edge[i].flow) return 0; 102 } 103 return 1; 104 } 105 int main(){ 106 int t,a,b,c; 107 scanf("%d",&t); 108 while(t--){ 109 scanf("%d%d",&n,&m); 110 vs=0; vt=n+1; NV=vt+1; NE=0; 111 memset(head,-1,sizeof(head)); 112 memset(deg,0,sizeof(deg)); 113 while(m--){ 114 scanf("%d%d%d",&a,&b,&c); 115 --deg[a]; ++deg[b]; 116 if(c==0) addEdge(a,b,1); 117 } 118 if(solve()) puts("possible"); 119 else puts("impossible"); 120 } 121 return 0; 122 }
转载于:https://www.cnblogs.com/WABoss/p/4851919.html
POJ1637 Sightseeing tour(判定混合图欧拉回路)相关推荐
- POJ - 1637 Sightseeing tour(混合图欧拉回路的求解--建图跑最大流)
题目链接:https://vjudge.net/contest/399194#problem/B The city executive board in Lund wants to construct ...
- 2095: [Poi2010]Bridges 二分+混合图欧拉回路(网络流)
好厉害的题啊QAQ,并不会做. 最大值最小想到是二分,然后就是一个混合图欧拉回路的问题. 混合图欧拉回路问题的解决: 我们首先想到有向图的欧拉回路,需满足的条件是每个点的入度等于出度.那么对于一个混合 ...
- BZOJ2095 POI2010 Bridges 【二分+混合图欧拉回路】
BZOJ2095 POI2010 Bridges Description YYD为了减肥,他来到了瘦海,这是一个巨大的海,海中有n个小岛,小岛之间有m座桥连接,两个小岛之间不会有两座桥,并且从一个小岛 ...
- TZOJ 2099 Sightseeing tour(网络流判混合图欧拉回路)
描述 The city executive board in Lund wants to construct a sightseeing tour by bus in Lund, so that to ...
- BZOJ 2095 [Poi2010]Bridges 二分 最大流(混合图欧拉回路)
题目大意:给出一张n个点m条边的联通图,无重边,每条边有正反两个权值.现要从点1出发经过每条边每个点一次,问最大边权最小是多少. 最大最小容易想到二分,问题是如何判断是否有欧拉回路. 图不连通自然没有 ...
- [BZOJ2095][Poi2010]Bridges 最大流(混合图欧拉回路)
2095: [Poi2010]Bridges Time Limit: 10 Sec Memory Limit: 259 MB Description YYD为了减肥,他来到了瘦海,这是一个巨大的海, ...
- Bzoj2095:[Poi2010]Bridges:混合图欧拉回路,网络流
题目链接:2095:[Poi2010]Bridges 二分答案建图后显然是混合图的欧拉回路,有向边删掉无向边随机定向计算入度-出度的差du[i],如果du[i]<0连边(i,T,-du[i]/2 ...
- POJ 1637 Sightseeing tour 混合图欧拉回路存在性判断
没有想到网络流还能解决这一类问题,完全想不到@_@ 一开始把所有的无向边制定任意方向有当做有向边看,然后统计每个点的入度和出度.以前有向图的欧拉回路判定是每个点的入读都等于出度,这样可以保证可以回到起 ...
- BZOJ 2095: [Poi2010]Bridges 混合图欧拉回路
YYD为了减肥,他来到了瘦海,这是一个巨大的海,海中有n个小岛,小岛之间有m座桥连接,两个小岛之间不会有两座桥,并且从一个小岛可以到另外任意一个小岛.现在YYD想骑单车从小岛1出发,骑过每一座桥,到达 ...
最新文章
- 22.CSS边框与背景【上】
- Scrapyd部署Scrapy框架项目
- 自学python有用么_Python自学可以吗?
- 机器学习生态全景图3.0
- mysql oracle 备份数据库备份_完整备份Oracle数据库
- kotlin 扩展类的功能_Kotlin程序| 扩展功能功能
- vuejs对象更新渲染_vue 数组和对象渲染问题
- 协议处理程序初始化失败_域间路由协议的内容有哪些 域间路由协议的内容介绍【详解】...
- 5页面放大再正常显示_一加5/5TFlyme8 9.9.24 功能一览
- Python多线程编程---(1)threading 模块 Thread 类
- java.lang.UnsatifiedLinkError错误一例:不同虚拟机之间的库不能共用
- 这九年来都在干嘛-兄弟连IT教育
- 08_Flask ORM 利用SQLAlchemy进行数据库增删改查
- QIIME2进阶四_QIIME2扩增子基因序列系统发育分析
- 数据挖掘中分类和聚类的区别
- Sun Studio 12 Update 1:C++ 用户指南
- 微软修改 MIT 项目原作者版权声明引发争议;白宫为提高开源安全性邀请软件行业者座谈;Ruby 3.1.0 发布 | 开源日报
- 养成良好的编程习惯-一个库一个文件夹
- 谷歌浏览器请求头格式化输出成 python dict字典
- 实录:HBA卡速率设置错误导致服务器无法识别存储
热门文章
- 出现身份验证错误,要求的函数不受支持,远程计算机:X.X.X.X,这可能是由于CredSSP加密Oracle修正
- Python 语言程序设计(1)
- 电子商务商品供应链概论
- python请输入星期几的第一个_python如何获取星期几
- iframe框架_性能优化去除iframe脚手架升级方案
- C++查漏补缺之浮点数内存表示
- 编译原理教程_4 语法分析
- windows10重装后锁定其他盘_电脑重装Windows10系统步骤
- 简述中断和 DMA 的区别。
- 计算机硬件中板卡目前设备有哪几种,呼叫中心所需的硬件设备都有哪些?