POJ 3259 Wormholes(判断负环&(Bellman-Ford|SPFA))
来源:互联网 发布:在农村淘宝开店 编辑:程序博客网 时间:2024/06/06 12:20
题目链接:kuangbin带你飞 专题四 最短路练习 F - Wormholes
题意
农场主拥有很多农场,在这些农场之间有很多条路,以及单向的虫洞,每条路走完会花费一定的时间,而冲动可以回到之前的时间,问农场主是否可以通过特定的路径看到出发前的自己?(也就是回到自己出发时间前的出发点)
思路
将农场看做点,路和虫洞看做边,那么显然虫洞是负权边,这样题目就转化为求给定图中是否有负环的问题了。
Bellman-Ford和SPFA都可以进行负环的判断,因为这两个算法以前都没用过,索性就都写了一下,慢慢熟练。
SPFA是对Bellman-Ford进行队列优化的改进版,但提交后反而比Bellman-Ford慢,这点挺奇怪的。
不知道是数据的原因,还是什么?
代码
Bellman-Ford
#include<iostream>#include<cstring>#include<cmath>#include<cstdio>#include<algorithm>using namespace std;const int N = 509;const int MAX = 0x3f3f3f3f;struct Edge{ int u, v, r;}edge[N*N+200];int d[N];bool Bellman_Ford(int n, int e, int src){ for(int i=1; i<=n; i++) d[i] = MAX; d[src] = 0; while(d[src] >= 0) { bool flag = true; for(int i=0; i<e; i++) { int u = edge[i].u; int v = edge[i].v; int to = d[u] + edge[i].r; if(d[v] > to) { d[v] = to; flag = false; } } if(flag) return d[src] < 0; } return 1;}int main(){ int T; scanf("%d", &T); while(T--) { int n, m, w; scanf("%d%d%d", &n, &m, &w); for(int i=0; i<m; i++) { int a, b, c; scanf("%d%d%d", &a, &b, &c); edge[i].u = a; edge[i].v = b; edge[i].r = c; edge[i+m].u = b; edge[i+m].v = a; edge[i+m].r = c; } for(int i=0; i<w; i++) { int a, b, c; scanf("%d%d%d", &a, &b, &c); edge[2*m+i].u = a; edge[2*m+i].v = b; edge[2*m+i].r = -c; } if(Bellman_Ford(n, m*2+w, 1)) printf("YES\n"); else printf("NO\n"); } return 0;}
SPFA
#include<iostream>#include<cstring>#include<cmath>#include<cstdio>#include<algorithm>#include<queue>using namespace std;const int N = 509;const int MAX = 0x3f3f3f3f;struct Edge{ int u, v, r, next;}edge[N*N+200];int d[N];int h[N];bool vis[N];int cnt[N];bool spfa(int n){ memset(vis, 0, sizeof(vis)); memset(cnt, 0, sizeof(cnt)); for(int i=1; i<=n; i++) d[i] = MAX; d[1] = 0; vis[1] = 1; cnt[1]++; queue<int> q; q.push(1); while(!q.empty()) { int x = q.front(); vis[x] = 0; q.pop(); for(int i = h[x]; i!=-1; i = edge[i].next) { int v = edge[i].v; int to = edge[i].r + d[edge[i].u]; if(d[v] > to) { d[v] = to; if(!vis[v]) { vis[v] = 1; q.push(v); if(++cnt[v] > n) return 1; } } } } return 0;}int main(){ int T; scanf("%d", &T); while(T--) { int n, m, w; memset(h, -1, sizeof(h)); scanf("%d%d%d", &n, &m, &w); for(int i=0; i<m; i++) { int a, b, c; scanf("%d%d%d", &a, &b, &c); edge[i].next = h[a]; edge[i].u = a; edge[i].v = b; edge[i].r = c; h[a] = i; edge[i+m].next = h[b]; edge[i+m].u = b; edge[i+m].v = a; edge[i+m].r = c; h[b] = i+m; } for(int i=0; i<w; i++) { int a, b, c; scanf("%d%d%d", &a, &b, &c); edge[2*m+i].next = h[a]; edge[2*m+i].u = a; edge[2*m+i].v = b; edge[2*m+i].r = -c; h[a] = 2*m+i; } if(spfa(n)) printf("YES\n"); else printf("NO\n"); } return 0;}
0 0
- POJ - 3259 Wormholes(判断负环, Bellman Ford,SPFA)
- POJ 3259 Wormholes(判断负环&(Bellman-Ford|SPFA))
- POJ 3259 Wormholes(判断负权回路|SPFA||Bellman-Ford)
- POJ 3259 Wormholes (判断负环,SPFA或Bellman-Ford都可)
- poj 3259 Wormholes 【Bellman-Ford 判断负环】
- POJ 3259 Wormholes (Bellman-Ford判断负环)
- poj 3259 Wormholes(SPFA || Bellman-Ford)
- poj 3259 Wormholes【Bellman-Ford Vs SPFA】
- poj 3259 Wormholes SPFA // Bellman-ford
- POJ 3259 Wormholes (Bellman-ford或SPFA)
- Bellman-Ford||SPFA-POJ-3259-Wormholes
- POJ 3259 Wormholes (SPFA&&BellMan Ford)
- 【POJ】3259 Wormholes bellman-ford | SPFA
- POJ:3259 Wormholes(SPFA判断负环)
- POJ 3259 Wormholes 【SPFA 判断负环】
- poj 3259 Wormholes 【SPFA&&判断负环】
- Poj 3259 Wormholes【spfa 负环判断】
- POJ 3259 Wormholes SPFA 判断负环
- iOS 【关于几个常用UIColor宏定义】
- 深入分析JavaWeb Item54 -- Spring中的AOP面向切面编程2
- linux删除普通用户报错 userdel: user fancy is currently used by process 1973
- 多线程学习
- 老人真是饿了(贪心)
- POJ 3259 Wormholes(判断负环&(Bellman-Ford|SPFA))
- H264的DTS和PTS
- C/C++小知识
- 【Scala】尾递归优化
- HRBUST 1037 组合数末尾的零
- IOS使用Xib创建自定义View
- 从模块化的角度看待CNN网络
- Implementing a virtual machine in C(虚拟机C语言实现)
- Python学习(三): 字符串操作