更加深入的了解SPFA

SPFA算法是求单源路径的经典算法,就是一点到其它所有点的最短路径。

这个类似于Flyod但是效率要高很多。下面给出具体的演示。

Minya Konka decided to go to Fuzhou to participate in the ACM regional contest at their own expense.Through the efforts, they got a small amount of financial support from their school, but the school could pay only one of those costs between two stations for them.

From SWUST to Fujian Normal University which is the contest organizer, there are a lot of transfer station and there are many routes.For example, you can take the bus to Mianyang Railway Station (airport), then take the train (plane) to Fuzhou,and then take a bus or taxi to the Fujian Normal University.

The school could pay only one of those costs between two stations for them, the others paid by the Minya Konka team members.They want to know what is the minimum cost the need pay.Can you calculate the minimum cost?

Input

There are several test cases.

In each case,the first line has two integers n(n<=100) and m(m<=500),it means there are n stations and m undirected roads.

The next m lines, each line has 3 integers u,v,w,it means there is a undirected road between u and v and it cost w.(1<=u,v<=n,0<=w<=100)

The ID of SWUST is 1,and n is the ID of Fujian Normal University.

Output

If they can not reach the destination output -1, otherwise output the minimum cost.

Sample Input

5 5

1 2 7

1 3 3

3 4 3

2 5 3

4 5 3
#include "iostream"
#include "cstring"
#include "queue"
using namespace std;
#define INF 999999999
#define eMax 505
#define nMax 105
bool vis[nMax];
int dis[2][nMax], num, rec[nMax], n, m;
struct Node
{
int u, v, w, pre;
}e[eMax*2];
void Init(int u, int v, int w)
{
e[num].u = u;
e[num].v = v;
e[num].w = w;
e[num].pre = rec[u];
rec[u] = num++;
}
void spfa(int s, int p)
{
memset(vis, false, sizeof(vis));
dis[p][s] = 0;
queue<int> q;
q.push(s);
while(!q.empty())
{
s = q.front();
q.pop();
vis[s] = false;
int j, v;
for(j=rec[s]; j!=-1; j=e[j].pre)
{
v = e[j].v;
if(dis[p][s] + e[j].w < dis[p][v])
{
dis[p][v]=dis[p][s]+e[j].w;
if(!vis[v])
{
vis[v] = true;
q.push(v);
}
}
}
}
}
int main()
{
int u, v, w;
while(cin>>n>>m)
{
num = 0;
memset(rec, -1, sizeof(rec));
memset(dis, 0x3f, sizeof(dis));
int ans = INF;
while(m--)
{
cin>>u>>v>>w;
Init(u, v, w);
Init(v, u, w);
}
spfa(1, 0);
spfa(n, 1);
for(int i=0; i<num; i++)
if(dis[0][e[i].u]+dis[1][e[i].v] < ans)
ans = dis[0][e[i].u]+dis[1][e[i].v];
if(ans < INF) cout<<ans<<endl;
else cout<<"-1"<<endl;
}
}
在上面的代码中我们用了一个二维的数组来分别保留
1到其它所有点的最短距离和n到其它所有点的最短距离。
就是这样,这个就是SPFA。

你可能感兴趣的:(SPFA)