題目連接ios
本題解來源算法
其餘連接jsp
卡spfa的數據組ide
題解spfa講解ui
來自以上題解的圖片來自常暗踏陰url
使用前向星鏈表存圖spa
直接用隊列優化spfa.net
struct cmp { bool operator()(int a,int b) { return dist[a]>dist[b]; } }; priority_queue<int,vector<int>,cmp> q;void dijspfa() { q.push(s); memset(inq,0,sizeof(inq)); memset(dist,0x7f,sizeof(dist)); dist[s]=0; while(!q.empty()) { int u=q.top(); q.pop();inq[u]=0; for(int j=first[u];j>0;j=e[j].nxt) { if(e[j].len+dist[u]<dist[e[j].to]) { dist[e[j].to]=dist[u]+e[j].len; if(inq[e[j].to]==0) { q.push(e[j].to);inq[e[j].to]=1; } } } } }
dijspfa特性code
1.判負環
spfa判負環主要用dfs,由於dfs判負環能夠及時退出防止超時,
數據強化能夠用bfs看下面
dijspfa判負環繼承spfa的功能
可是可能過不了233
SPjkstra算法--就是本文的dijspfa
2.與dij,spfa比較
dij的思想是堆優化後從小到大鬆弛,每一個點只入隊一次
spfa的思想是不斷修改子節點,使每一個點重複入隊更新,所以能夠判負環
時間差別就在重複入隊上
完整代碼
1 #include<iostream> 2 #include<queue> 3 #include<cstdio> 4 #include<cstring> 5 #define Mx 200001 6 #define Nx 100001 7 using namespace std; 8 struct edge 9 { 10 int to,nxt,len; 11 }e[Mx]; 12 int first[Nx]; int n,m,s; 13 void addstar(int i,int u,int v,int w) 14 { 15 e[i].len=w; 16 e[i].nxt=first[u]; 17 e[i].to=v; 18 first[u]=i; 19 } 20 int inq[Nx]; 21 int dist[Nx]; 22 23 struct cmp 24 { 25 bool operator()(int a,int b) 26 { 27 return dist[a]>dist[b]; 28 } 29 }; 30 31 priority_queue<int,vector<int>,cmp> q; 32 void dijspfa() 33 { 34 q.push(s); 35 memset(inq,0,sizeof(inq)); 36 memset(dist,0x7f,sizeof(dist)); 37 dist[s]=0; 38 while(!q.empty()) 39 { 40 int u=q.top(); 41 q.pop();inq[u]=0; 42 for(int j=first[u];j>0;j=e[j].nxt) 43 { 44 if(e[j].len+dist[u]<dist[e[j].to]) 45 { 46 dist[e[j].to]=dist[u]+e[j].len; 47 if(inq[e[j].to]==0) 48 { 49 q.push(e[j].to);inq[e[j].to]=1; 50 } 51 } 52 } 53 } 54 } 55 int main() 56 { 57 memset(first,0,sizeof(first)); 58 cin>>n>>m>>s; 59 for(int i=1;i<=m;++i) 60 { 61 int a,b,c; 62 cin>>a>>b>>c; 63 addstar(i,a,b,c); 64 } 65 dijspfa(); 66 for(int i=1;i<=n;++i) 67 { 68 cout<<dist[i]<<" "; 69 } 70 return 0; 71 }