1. 程式人生 > 實用技巧 >判負環(bellman-ford | | spfa)

判負環(bellman-ford | | spfa)

bellman-ford判負環,據bellman-ford的性質最後得出的是通過不超過n-1條邊的從起點到其他點的最短距離(因為n個點,所以n-1條邊)

但是如果在n-1次迴圈之後仍然存在邊可以被鬆弛,那麼就存在負環(因為如果沒有負環n-1次就已經確定了最短距離,具體可參考bellman-ford證明,已經是最短距離了還能被鬆弛,必然是存在負環)

 1 #include<iostream>
 2 using namespace std;
 3 const int N=2010,M=1e5+10;
 4 int n,m;
 5 struct edge{
 6     int a,b,w;
7 }edges[M]; 8 int dis[N]; 9 void bellman_ford(){ 10 //直接把dis初始化為全0就可以了,意思就是所有的點都是起點 11 for(int i=0;i<n-1;i++){ 12 for(int j=0;j<m;j++){ 13 auto t=edges[j]; 14 if(dis[t.b]>dis[t.a]+t.w){ 15 dis[t.b]=dis[t.a]+t.w; 16 } 17 }
18 } 19 } 20 int main(void){ 21 cin>>n>>m; 22 for(int i=0;i<m;i++){ 23 int a,b,c; 24 cin>>a>>b>>c; 25 edges[i]={a,b,c}; 26 } 27 bellman_ford(); 28 for(int j=0;j<m;j++){ 29 auto t=edges[j]; 30 if(dis[t.b]>dis[t.a]+t.w){
31 cout<<"Yes"; 32 return 0; 33 } 34 } 35 cout<<"No"; 36 return 0; 37 }

spfa判負環

 1 #include<iostream>
 2 #include<queue>
 3 #include<cstring>
 4 using namespace std;
 5 const int N=2010,M=1e5+10;
 6 int n,m;
 7 int h[N],e[M],w[M],ne[M],idx;
 8 int dis[N],cnt[N];
 9 bool st[N];
10 void add(int a,int b,int c){
11     e[idx]=b,w[idx]=c,ne[idx]=h[a],h[a]=idx++;
12 }
13 bool spfa(){
14     queue<int> q;
15     for(int i=1;i<=n;i++){
16         q.push(i);
17         st[i]=true;
18     }//把所有的點都丟進佇列裡面
19     while(q.size()){
20         int t=q.front();
21         q.pop();
22         st[t]=false;
23         for(int i=h[t];i!=-1;i=ne[i]){
24             int j=e[i];
25             if(dis[j]>dis[t]+w[i]){
26                 dis[j]=dis[t]+w[i];
27                 cnt[j]=cnt[t]+1;
28                 if(cnt[j]>=n){
29                     return true;
30                 }
31                 if(!st[j]){
32                     q.push(j);
33                     st[j]=true;
34                 }
35             }
36         }
37     }
38     return false;
39 }
40 int main(void){
41     cin>>n>>m;
42     memset(h,-1,sizeof(h));
43     for(int i=0;i<m;i++){
44         int a,b,c;
45         cin>>a>>b>>c;
46         add(a,b,c);
47     }
48     if(spfa()){
49         cout<<"Yes";
50     }else{
51         cout<<"No";
52     }
53     return 0;
54 }