混合图(既有有向边又有无向边的图)中欧拉环、欧拉路径的判定需要借助网络流!(1)欧拉环的判定:
一开始当然是判断原图的基图是否连通,若不连通则一定不存在欧拉环或欧拉路径(不考虑度数为0的点)。其实,难点在于图中的无向边,需要对所有的无向边定向(指定一个方向,使之变为有向边),使整个图变成一个有向欧拉图(或有向半欧拉图)。若存在一个定向满足此条件,则原图是欧拉图(或半欧拉图)否则不是。关键就是如何定向?首先给原图中的每条无向边随便指定一个方向(称为初始定向),将原图改为有向图G',然后的任务就是改变G'中某些边的方向(当然是无向边转化来的,原混合图中的有向边不能动)使其满足每个点的入度等于出度。
设D[i]为G'中(点i的出度 - 点i的入度)。可以发现,在改变G'中边的方向的过程中,任何点的D值的奇偶性都不会发生改变(设将边<i, j>改为<j, i>,则i入度加1出度减1,j入度减1出度加1,两者之差加2或减2,奇偶性不变)!而最终要求的是每个点的入度等于出度,即每个点的D值都为0,是偶数,故可得:若初始定向得到的G'中任意一个点的D值是奇数,那么原图中一定不存在欧拉环!若初始D值都是偶数,则将G'改装成网络:设立源点S和汇点T,对于每个D[i]>0的点i,连边<S, i>,容量为D[i]/2;对于每个D[j]<0的点j,连边<j, T>,容量为-D[j]/2;G'中的每条边在网络中仍保留,容量为1(表示该边最多只能被改变方向一次)。求这个网络的最大流,若S引出的所有边均满流,则原混合图是欧拉图,将网络中所有流量为1的中间边(就是不与S或T关联的边)在G'中改变方向,形成的新图G”一定是有向欧拉图;若S引出的边中有的没有满流,则原混合图不是欧拉图。为什么能这样建图?
考虑网络中的一条增广路径S-->i-->...-->j-->T,将这条从i到j的路径在G'中全部反向,则:i的入度加1出度减1,j的入度减1出度加1,路径中其它点的入度出度均不变。而i是和S相连的,因此初始D[i]>0,即i的出度大于入度,故这样反向之后D[i]减少2;同理,j是和T相连的,这样反向之后D[j]增加2。因此,若最大流中边<S, i>满流(流量为初始D[i]/2),此时D[i]值就变成了0,也就是i的入度等于出度。因此只要使所有S引出的边全部满流,所有初始D值>0的点的D值将等于0,又因为将边变向后所有点的D值之和不变,所有初始D值小于0的点的D值也将等于0,而初始D值等于0的D点既不与S相连也不与T相连,所以它们是网络中的中间点,而中间点的流入量等于流出量,故它们的入度和出度一直不变,即D值一直为0。因此,整个图G'成为欧拉图。(2)欧拉路径的判定:
首先可以想到的是枚举欧拉路径的起点i和终点j,然后在图中添加边<j, i>,再求图中是否有欧拉回路即可。但是,该算法的时间复杂度达到了O(M * 最大流的时间),需要优化。
前面已经说过,在将边变向的过程中任何点的D值的奇偶性都不会改变,而一个有向图有欧拉路径的充要条件是基图连通且有且只有一个点的入度比出度少1(作为欧拉路径的起点),有且只有一个点的入度比出度多1(作为终点),其余点的入度等于出度。这就说明,先把图中的无向边随便定向,然后求每个点的D值,若有且只有两个点的初始D值为奇数,其余的点初始D值都为偶数,则有可能存在欧拉路径(否则不可能存在)。进一步,检查这两个初始D值为奇数的点,设为点i和点j,若有D[i]>0且D[j]<0,则i作起点j作终点(否则若D[i]与D[j]同号则不存在欧拉路径),连边<j, i>,求是否存在欧拉环即可(将求出的欧拉环中删去边<j, i>即可)。这样只需求一次最大流。
Code:
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<queue>
#include<cmath>
#include<iostream>
using namespace std;
const int N=205,M=20005,INF=0x3f3f3f3f;
int t,S,T,n,m,cnt,tot;
int cur[N],Head[N],h[N],Q[N],d[N];
struct Noe{int to,Next,v;
}Edge[M];
void insert(int u,int v,int w){Edge[++cnt].to=v;Edge[cnt].Next=Head[u];Head[u]=cnt;Edge[cnt].v=w;Edge[++cnt].to=u;Edge[cnt].Next=Head[v];Head[v]=cnt;Edge[cnt].v=0;
}
bool bfs(){int head=0,tail=1;memset(h,-1,sizeof(h));Q[0]=S;h[S]=0;while(head!=tail){int now=Q[head++];for(int i=Head[now];i;i=Edge[i].Next){if(Edge[i].v&&h[Edge[i].to]==-1){h[Edge[i].to]=h[now]+1;Q[tail++]=Edge[i].to;}}}return h[T]!=-1;
}
int dfs(int x,int f){if(x==T){return f;}int w,used=0;for(int i=cur[x];i;i=Edge[i].Next){if(h[Edge[i].to]==h[x]+1){w=dfs(Edge[i].to,min(f-used,Edge[i].v));Edge[i].v-=w;Edge[i^1].v+=w;if(Edge[i].v){cur[x]=i;}used+=w;if(used==f){return f;}}}if(!used){h[x]=-1;}return used;
}
int dinic(){int tmp=0;while(bfs()){for(int i=S;i<=T;i++){cur[i]=Head[i];}tmp+=dfs(S,INF);}return tmp;
}
bool judge(){for(int i=1;i<=n;i++){if(d[i]%2!=0){return 0;}}return 1;
}
int main(){int u,v,opt;scanf("%d",&t);while(t--){memset(Head,0,sizeof(Head));memset(d,0,sizeof(d));cnt=1,tot=0;scanf("%d%d",&n,&m);T=n+1;for(int i=1;i<=m;i++){scanf("%d%d%d",&u,&v,&opt);d[u]++;d[v]--;if(opt==0){insert(u,v,1);}}for(int i=1;i<=n;i++){if(d[i]<0){insert(i,T,-d[i]/2);}if(d[i]>0){insert(0,i,d[i]/2);tot+=d[i]/2;}}if(!judge()){printf("impossible\n");continue;}if(tot!=dinic()){printf("impossible\n");}else{printf("possible\n");}}return 0;
}

转载于:https://www.cnblogs.com/ukcxrtjr/p/11295264.html

混合图的欧拉路径和欧拉回路判断相关推荐

  1. POJ 1637 混合图的欧拉回路判定

    题意:一张混合图,判断是否存在欧拉回路. 分析参考: 混合图(既有有向边又有无向边的图)中欧拉环.欧拉路径的判定需要借助网络流! (1)欧拉环的判定: 一开始当然是判断原图的基图是否连通,若不连通则一 ...

  2. 欧拉回路(混合图的欧拉回路)

    /* ID: linjd821 LANG: C++ TASK: sightseeing */ //zju 1992 //混合图的欧拉回路,用网络流调整无向边 /* //转自某位牛人blog 混合图欧拉 ...

  3. POJ 1637 混合图的欧拉回路 + Dinic

    题意 传送门 POJ 1637 题解 有向图存在欧拉回路的充要条件: 所有顶点入度等于出度,且图为连通图. 混合图存在欧拉回路的判断的基本思路: 混合图 G(V,E)G(V,E)G(V,E) 通过假设 ...

  4. BZOJ 2095 [Poi2010]Bridges 二分 最大流(混合图欧拉回路)

    题目大意:给出一张n个点m条边的联通图,无重边,每条边有正反两个权值.现要从点1出发经过每条边每个点一次,问最大边权最小是多少. 最大最小容易想到二分,问题是如何判断是否有欧拉回路. 图不连通自然没有 ...

  5. [BZOJ2095][Poi2010]Bridges 最大流(混合图欧拉回路)

    2095: [Poi2010]Bridges Time Limit: 10 Sec  Memory Limit: 259 MB Description YYD为了减肥,他来到了瘦海,这是一个巨大的海, ...

  6. poj 1637(混合图求欧拉回路)

    参考博客:http://www.cnblogs.com/destinydesigner/archive/2009/09/28/1575674.html 1 定义 欧拉通路 (Euler tour)-- ...

  7. poj1637(混合图判欧拉回路)

    把该图的无向边随便定向,计算每个点的入度和出度.如果有某个点出入度 之差为奇数,那么肯定不存在欧拉回路.因为欧拉回路要求每点入度 = 出度, 也就是总度数为偶数,存在奇数度点必不能有欧拉回路.  好了 ...

  8. 2095: [Poi2010]Bridges 二分+混合图欧拉回路(网络流)

    好厉害的题啊QAQ,并不会做. 最大值最小想到是二分,然后就是一个混合图欧拉回路的问题. 混合图欧拉回路问题的解决: 我们首先想到有向图的欧拉回路,需满足的条件是每个点的入度等于出度.那么对于一个混合 ...

  9. BZOJ2095 POI2010 Bridges 【二分+混合图欧拉回路】

    BZOJ2095 POI2010 Bridges Description YYD为了减肥,他来到了瘦海,这是一个巨大的海,海中有n个小岛,小岛之间有m座桥连接,两个小岛之间不会有两座桥,并且从一个小岛 ...

最新文章

  1. ERROR: No query specified(Mysql数据库报错)
  2. 爱慕内衣信息化颠覆流程重构供应链
  3. matlab imformats,그래픽스 파일에 이미지 쓰기
  4. reactNative之react-native-picker
  5. 火星时代Web前端开发完整版
  6. 使用arduino作为programer对新的mcu烧录bootloader
  7. 什么是OCR?如何使用OCR文字识别软件?
  8. PS:将一个图片变成圆形
  9. 图解通信原理与案例分析-28:四大全球卫星导航系统GNSS的基本原理与技术对比---中国的北斗、美国的GPS、欧洲的伽利略、俄罗斯的格洛纳斯
  10. 锐度、对比度、和清晰度的区别
  11. Typec手机有线网卡网线转网口转接口快充方案
  12. 星起航:抖音小店截流是什么,怎么玩?
  13. 体会现实生活的两个月(上)
  14. 十年阿里P6大牛谈外包!
  15. 如何在计算机桌面上增添word,word在电脑桌面的图标不见了怎么办
  16. 理解前端框架、前端库,两者有什么区别
  17. 设置idea打开时显示选择项目窗口
  18. Actix-Web学习
  19. 什么是事务,事务的四个特性是什么
  20. RPA之家-Attended Automation

热门文章

  1. Struts2理解——转发和重定向
  2. Windows Containers 大冒险: 加速
  3. hdu4932 Miaomiao#39;s Geometry (BestCoder Round #4 枚举)
  4. jetbrains从入门到卸载 (前言) 为什么要jetbrains
  5. JavaScript之引用类型介绍
  6. nginx + Lua 实现自定义WAF
  7. mybatis开发常见SQL使用手册
  8. 怒卸python3.4.1
  9. JavaScript:动态选中CheckBox
  10. 一键Ghost 脱机下载不再愁