Constructing Roads(spfa)

http://acm.sdut.edu.cn/sdutoj/problem.php?action=showproblem&problemid=2493

 1 #include <stdio.h>
 2 #include <string.h>
 3 #include <queue>
 4 using namespace std;
 5 const int maxn=1010;
 6 const int maxm=maxn*maxn;
 7 const long long INF=1LL<<60;
 8 int vis[maxn],head[maxn];
 9 int n,m,cnt = 0;
10 struct node
11 {
12     int u,v;
13     long long w;
14     int next;
15 
16 } edge[maxm];
17 
18 inline void add(int u,int v,long long w)
19 {
20     edge[cnt].u = u;
21     edge[cnt].v = v;
22     edge[cnt].w = w;
23     edge[cnt].next = head[u];
24     head[u] = cnt++;
25 }
26 
27 void spfa(int s, long long dis[])
28 {
29 
30     queue<int>q;
31     q.push(s);
32     vis[s] = 1;
33     dis[s] = 0;
34     while(!q.empty())
35     {
36         int u = q.front();
37         q.pop();
38         vis[u] = 0;
39         for (int j = head[u]; j!=-1; j= edge[j].next)
40         {
41             int v = edge[j].v;
42             long long w = edge[j].w;
43             if (dis[u]+w < dis[v])
44             {
45                 dis[v] = dis[u]+w;
46                 q.push(v);
47                 vis[v] = 1;
48             }
49         }
50     }
51 
52 }
53 void init()
54 {
55 
56 }
57 int main()
58 {
59     int u,v;
60     long long w;
61     long long dis1[maxn],dis2[maxn];
62     while(~scanf("%d %d",&n,&m))
63     {
64         for (int i = 0; i <= n; i++)
65         {
66             vis[i] = 0;
67             dis1[i] = INF;
68             dis2[i] = INF;
69             head[i] = -1;
70         }
71         cnt = 0;
72         for (int i = 0; i < m; i++)
73         {
74             scanf("%d %d %lld",&u,&v,&w);
75             add(u,v,w);
76             add(v,u,w);
77         }
78         int s,e;
79         long long min=INF;
80         scanf("%d %d",&s,&e);
81         spfa(s,dis1);//求出起点到所有点的最短路径
82         spfa(e,dis2);//求出终点到所有点的最短路径
83         for (int i = 0; i < cnt; i++)//遍历所有的边
84         {
85             u = edge[i].u;
86             v = edge[i].v;
87             w = edge[i].w;
88             if (dis1[u]+dis2[v]+w/2 < min)//S->u+e->v+w/2即为改变后的权值,找出最小的
89                 min = dis1[u]+dis2[v]+w/2;
90         }
91         if(min==INF)
92         {
93             puts("No solution");
94             continue;
95         }
96         printf("%lld
",min);
97     }
98     return 0;
99 }
View Code
原文地址:https://www.cnblogs.com/lahblogs/p/3441649.html