【SPFA判断负环】BZOJ1715- [Usaco2006 Dec]Wormholes 虫洞

【题目大意】

判断一张图中是否存在负环。

【思路】

dfs版SPFA。

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 struct edge
 4 {
 5     int to,len;
 6 };
 7 const int MAXN=500+5;
 8 vector<edge> E[MAXN];
 9 int f,n,m,w;
10 int vis[MAXN],dis[MAXN],flag;
11 
12 void addedge(int s,int e,int t)
13 {
14     E[s].push_back((edge){e,t});
15 }
16 
17 void init()
18 {
19     scanf("%d%d%d",&n,&m,&w);
20     for (int i=0;i<MAXN;i++) vector<edge>().swap(E[i]); 
21     for (int i=1;i<=m;i++)
22     {
23         int s,e,t;
24         scanf("%d%d%d",&s,&e,&t);
25         addedge(s,e,t);
26         addedge(e,s,t);
27     }
28     for (int i=1;i<=w;i++)
29     {
30         int s,e,t;
31         scanf("%d%d%d",&s,&e,&t);
32         addedge(s,e,-t);
33     }
34 }
35 
36 void spfa(int u)
37 {
38     if (vis[u])
39     {
40         flag=1;
41         return;
42     }
43     vis[u]=1;
44     for (int i=0;i<E[u].size();i++)
45     {
46         int to=E[u][i].to,len=E[u][i].len;
47         if (dis[to]>dis[u]+len)
48         {
49             dis[to]=dis[u]+len;
50             spfa(to);
51             if (flag) return;
52         }
53     }
54     vis[u]=0;
55 }
56 
57 void solve()
58 {
59     memset(vis,0,sizeof(vis));
60     flag=0;
61     for (int i=1;i<=n;i++)
62     {
63         spfa(i);
64         if (flag) break; 
65     } 
66     puts(flag?"YES":"NO");
67 }
68 
69 int main()
70 {
71     scanf("%d",&f);
72     while (f--)
73     {    
74         init();
75         solve();
76     }
77 
78     return 0;
79 }
原文地址:https://www.cnblogs.com/iiyiyi/p/6058167.html