第K短路(A*演算法)
阿新 • • 發佈:2018-12-30
對於無向圖:
SPFA+A*演算法:先用SPFA求目標結點到各個結點的最短路徑;然後,取g(x)為從初始結點到當前結點x的路徑長度,h(x)為從x結點到目標結點的最短路徑長度,即h(x)取dis[x]即可,估價函式f(x)=g(x)+h(x)。
對於有向圖:
SPFA+A*演算法:顯然應將有向邊取反,然後求目標節點到各個結點的最短路徑;後面和上述一樣。
程式碼:
struct node { int u; int w; node (int uu,int ww):u(uu),w(ww){} }; void SPFA(int t) { int i; for(i=0;i<=n;i++) { dis[i]=inf; vis[i]=0; } dis[t]=0; queue<int>que; que.push(t); vis[t]=1; while(!que.empty()) { int u=que.front(); que.pop(); vis[u]=0; for(i=0;i<g[u].size();i++) { node b=g[u][i]; int v=b.u; if(dis[v]>dis[u]+b.w) { dis[v]=dis[u]+b.w; if(!vis[v]) { vis[v]=1; que.push(v); } } } } } struct cnode { int u; int len; cnode (int uu,int ww):u(uu),len(ww){} friend bool operator < (cnode a,cnode b)//過載比較運算子 { return a.len+dis[a.u]>b.len+dis[b.u];//g(x)=a.len,h(x)=dis[a.u] } }; int A_star(int s) { int i; if(dis[s]==inf)return -1;//若s到t不連通的話,提前終止 priority_queue<cnode>que; memset(cnt,0,sizeof(cnt)); que.push(cnode(s,0)); while(!que.empty()) { cnode a=que.top();que.pop(); int u=a.u; int len=a.len; cnt[u]++; if(cnt[t]==k) return len;//k=1,最短路,k=n,第k短路 for(i=0;i<g[u].size();i++) { node b=g[u][i]; int v=b.u; que.push(cnode(v,len+b.w)); } } return -1; }