没有想到网络流还能解决这一类问题,完全想不到@_@

一开始把所有的无向边制定任意方向有当做有向边看,然后统计每个点的入度和出度。以前有向图的欧拉回路判定是每个点的入读都等于出度,这样可以保证可以回到起点,现在在一些边可以调换方向的情况下,所有定点的入度和出度之差必定为偶数,因为调换任意一条边的方向都会使两个定点的入度和出度变化2,所以要构成一个欧拉回路所有点的入度和出度之差都为偶数,并设差为deg。

现在问题转化成了能否通过改变一些边的方向来是的所有点的入度出度都为0,因为有向边的方向已经确定,不用理会,把他们全部都删去。剩下的边中如果有出度大于入度的,肯定要调换-deg/2条边来使其变成0,建立源点到这些点的边,容量为-deg/2,同理,有出入大于入度的,就建立这些点到汇点的边,容量同样为deg/2。其他的边容量都为1,然后做一遍最大流,如果流量和需要调换的边数相等,即源点出去的边全部都满载,就有欧拉回路存在,否则不存在欧拉回路。

为什么这样子是成立的,我的想法是这样的,除了连接源点和汇点的边之外,其他的边的容量都为1,1的流量对应的就是一条边,源点连接到一个点的时候的容量为t,如果满载相当于这个点出发的t条边满载,相当于调换了t条边,但是这样子会影响后面的边的度,不过因为流会一直流到汇点,中途所有的满载的边都是要调换的,所以中间原本度为0的点的度其实到最后不会改变。

#include <cstdio>
#include <cstring>
#include <cmath>
#include <algorithm>
#include <climits>
#include <string>
#include <iostream>
#include <map>
#include <cstdlib>
#include <list>
#include <set>
#include <queue>
#include <stack>using namespace std;typedef long long LL;
const int maxn = 205;
const int INF = INT_MAX / 3;struct Edge {int u,v,cap;Edge(int u,int v,int cap):u(u),v(v),cap(cap) {}
};int n,m,incnt[maxn],outcnt[maxn];
int deg[maxn],s,t;
vector<Edge> edges;
vector<int> e[maxn];void adde(int u,int v,int w) {int m = edges.size();edges.push_back(Edge(u,v,w));edges.push_back(Edge(v,u,0));e[u].push_back(m);e[v].push_back(m ^ 1);
}int level[maxn],q[maxn * 2],qs,qe;
bool bfs() {//建立层次网络memset(level,0,sizeof(level));level[s] = 1;qs = qe = 0;q[qe++] = s;while(qs < qe) {int now = q[qs++],nm = e[now].size();if(now == t) break;for(int i = 0;i < nm;i++) {Edge &ne = edges[e[now][i]];if(ne.cap && level[ne.v] == 0) {level[ne.v] = level[now] + 1;q[qe++] = ne.v;}}}return level[t];
}int dfs(int now,int alpha) {if(now == t) return alpha;int sum = 0,nm = e[now].size();for(int i = 0;i < nm;i++) {Edge &ne = edges[e[now][i]];if(level[now] + 1 == level[ne.v] && ne.cap && alpha) {int ret = dfs(ne.v,min(alpha,ne.cap));ne.cap -= ret; edges[e[now][i] ^ 1].cap += ret;sum += ret; alpha -= ret;}}if(sum == 0) level[now] = -1;return sum;
}void dinic() {while(bfs()) dfs(s,INF);
}bool solve() {s = 0; t = n + 1;//判断入度出度之差是否为偶数for(int i = 1;i <= n;i++) {deg[i] = incnt[i] - outcnt[i];if(deg[i] & 1) return false;}//建立容量网络for(int i = 1;i <= n;i++) {//如果入度小于出度,建立从起点到这个点的边,容量为deg/2if(deg[i] < 0) adde(s,i,-deg[i] / 2);//如果出度大于入读,建立从当前点到汇点的边,容量同样为deg/2if(deg[i] > 0) adde(i,t,deg[i] / 2);}//计算最大流dinic();//判断从源点出发的所有边是否满流int m = e[s].size();for(int i = 0;i < m;i++) {if(edges[e[s][i]].cap != 0) return false;}return true;
}int main() {int T; scanf("%d",&T);while(T--) {scanf("%d%d",&n,&m);edges.clear();for(int i = 0;i <= n + 1;i++) e[i].clear();memset(incnt,0,sizeof(incnt));memset(outcnt,0,sizeof(outcnt));for(int i = 1;i <= m;i++) {int u,v,c; scanf("%d%d%d",&u,&v,&c);//先将无向边全部作为有向边处理incnt[v]++; outcnt[u]++;//无向边存起来if(c == 0) adde(u,v,1);}if(solve()) puts("possible");else puts("impossible");}return 0;
}

  

转载于:https://www.cnblogs.com/rolight/p/3871431.html

POJ 1637 Sightseeing tour 混合图欧拉回路存在性判断相关推荐

  1. poj 1637 Sightseeing tour 混合欧拉图判定

    POJ - 1637点我点我:-) Sightseeing tour Time Limit: 1000MS   Memory Limit: 10000KB   64bit IO Format: %ll ...

  2. poj 1637 Sightseeing tour——最大流+欧拉回路

    题目:http://poj.org/problem?id=1637 先给无向边随便定向,如果一个点的入度大于出度,就从源点向它连 ( 入度 - 出度 / 2 ) 容量的边,意为需要流出去这么多:流出去 ...

  3. poj 1637 Sightseeing tour 混合欧拉 最大流

    #include <cstdio> #include <vector> #include <queue> #include <cstring> usin ...

  4. POJ 1637 Sightseeing tour(最大流)

    POJ 1637 Sightseeing tour 题目链接 题意:给一些有向边一些无向边,问能否把无向边定向之后确定一个欧拉回路 思路:这题的模型很的巧妙,转一个http://blog.csdn.n ...

  5. POJ - 1637 Sightseeing tour(混合图欧拉回路的求解--建图跑最大流)

    题目链接:https://vjudge.net/contest/399194#problem/B The city executive board in Lund wants to construct ...

  6. poj 1637 Sightseeing tour

    http://poj.org/problem?id=1637 题意: 给出一张混合图,判断是否存在欧拉回路 原理: 1.存在欧拉回路的充要条件:所有点入度=出度 2.给无向边随便定向不会影响点的|出度 ...

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

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

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

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

  9. TZOJ 2099 Sightseeing tour(网络流判混合图欧拉回路)

    描述 The city executive board in Lund wants to construct a sightseeing tour by bus in Lund, so that to ...

最新文章

  1. 如何提取cocos iOS应用程序APP与游戏安装包里的资源与文件
  2. linux 信号 core,Shell 信号发送与捕捉
  3. frontend badi
  4. .net core 生成二维码
  5. 课时109.外边距合并现象(掌握)
  6. uboot启动过程总结的思维导图
  7. CSS3实现卡片翻转动画
  8. mysql 的下划线搜索转义
  9. 人工智能的未来-揭示人类思维的奥秘How to create a mind - Ray Kurzweil
  10. 关于天猫魔盒tmb100系列 开机灯亮显示器无反应的问题分析
  11. 最强半自动化抓鸡工具打造思路
  12. javaweb(ssh)体育赛事网上售票系统案例
  13. IPD开发流程TR1-TR6各个阶段简介
  14. 百度贴吧签到(基于python3)
  15. Go:一次 exit code 是 137 且 无 coredump 的排错经历
  16. “假努力”与“假关心”
  17. iOS-APP性能测试
  18. UVa 1645 Count
  19. Android音视频开发之,全网疯传
  20. 浙大PAT甲级-1017

热门文章

  1. python支持list类型吗_Python Numpy不支持的操作数类型“list”“list”
  2. 【算法竞赛学习】资金流入流出预测-挑战Baseline_数据探索与分析1
  3. 西交利物浦计算机专业分数线,西交利物浦大学2018年各省及各专业录取分数线及最低录投档线【理科 文科】...
  4. 图论--一般带花树匹配
  5. [机器学习] 模型稳定度指标PSI
  6. memset()函数用法
  7. 迁移学习 迁移参数_迁移学习简介
  8. PHP(三)——PHP基础知识
  9. DOA——ESPRIT算法
  10. Linux(fedora 10)Hello World模块