Silver Cow Party POJ - 3268

Posted mzchuan

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Silver Cow Party POJ - 3268相关的知识,希望对你有一定的参考价值。

One cow from each of N farms (1 ≤ N ≤ 1000) conveniently numbered 1..N is going to attend the big cow party to be held at farm #X (1 ≤ X ≤ N). A total of M (1 ≤ M ≤ 100,000) unidirectional (one-way roads connects pairs of farms; road i requires Ti (1 ≤ Ti ≤ 100) units of time to traverse.

Each cow must walk to the party and, when the party is over, return to her farm. Each cow is lazy and thus picks an optimal route with the shortest time. A cow‘s return route might be different from her original route to the party since roads are one-way.

Of all the cows, what is the longest amount of time a cow must spend walking to the party and back?

Input

Line 1: Three space-separated integers, respectively: NM, and X 
Lines 2.. M+1: Line i+1 describes road i with three space-separated integers: AiBi, and Ti. The described road runs from farm Ai to farm Bi, requiring Ti time units to traverse.

Output

Line 1: One integer: the maximum of time any one cow must walk.

Sample Input

4 8 2
1 2 4
1 3 2
1 4 7
2 1 1
2 3 5
3 1 2
3 4 4
4 2 3

Sample Output

10

Hint

Cow 4 proceeds directly to the party (3 units) and returns via farms 1 and 3 (7 units), for a total of 10 time units.
 
题意:第一行输入n,m,x。有n个点,每个点上都有一只牛,两个点之间有通道,通道是单向的,,往下m行输入的是两个点的编号和通过通道的时间,问每个牛都去x点聚会并回来,其中牛花费的最长时间是多少。注意,去的道路可能与回来的道路不同。
 
思路:最短路求法,但有一点不同,需要n点中除x点以外,其他点到x点又回家的时间和的最大值,可以以x为起点,从x到其他点为回家,从其他点到x为去,两个dijsktra算法即可,一个正向图,一个反向图。
 
代码:
  1 #include <cstdio>
  2 #include <fstream>
  3 #include <algorithm>
  4 #include <cmath>
  5 #include <deque>
  6 #include <vector>
  7 #include <queue>
  8 #include <string>
  9 #include <cstring>
 10 #include <map>
 11 #include <stack>
 12 #include <set>
 13 #include <sstream>
 14 #include <iostream>
 15 #define mod 998244353
 16 #define eps 1e-6
 17 #define ll long long
 18 #define INF 0x3f3f3f3f
 19 using namespace std;
 20 
 21 //ma用来存放两个点之间的距离
 22 int ma[1010][1010];
 23 //dis用来存放到1之间的距离
 24 int  dis1[1010];
 25 int  dis2[1010];
 26 //vis数组标记已经找过的最大起重
 27 bool vis[1010];
 28 
 29 //从x到其他地方的正向图
 30 void dijkstra1(int m,int q)
 31 
 32     memset(vis,0,sizeof(vis));
 33     memset(dis1,INF,sizeof(dis1));
 34     vis[q]=0;
 35     //初始时间为0;
 36     dis1[q]=0;
 37     for(int i=1;i<=m;i++)
 38     
 39         int mi=INF;
 40         int k=-1;
 41         //寻找x到其他地方的最小值
 42         for(int j=1;j<=m;j++)
 43         
 44             if(!vis[j]&&mi>dis1[j])
 45             
 46                 mi=dis1[j];
 47                 k=j;
 48             
 49         
 50         //如果没有最小值,则退出循环
 51         if(k==-1)
 52         
 53             break;
 54         
 55         vis[k]=1;
 56         for(int j=1;j<=m;j++)
 57         
 58             //从x到k的时间与从k到其他地方的时间之和与从x到其他地方的时间取最小值
 59             dis1[j]=min(dis1[j],dis1[k]+ma[k][j]);    
 60         
 61     
 62 
 63 //从x到其他地方的反向图
 64 void dijkstra2(int m,int q)
 65 
 66     memset(vis,0,sizeof(vis));
 67     memset(dis2,INF,sizeof(dis2));
 68     vis[q]=0;
 69     //初始时间为0;
 70     dis2[q]=0;
 71     for(int i=1;i<=m;i++)
 72     
 73         int mi=INF;
 74         int k=-1;
 75         //寻找x到其他地方的最小值
 76         for(int j=1;j<=m;j++)
 77         
 78             if(!vis[j]&&mi>dis2[j])
 79             
 80                 mi=dis2[j];
 81                 k=j;
 82             
 83         
 84         //如果没有最小值,则退出循环
 85         if(k==-1)
 86         
 87             break;
 88         
 89         vis[k]=1;
 90         for(int j=1;j<=m;j++)
 91         
 92             //从x到k的时间与从其他地方到k的时间之和与从x到其他地方的时间取最小值
 93             dis2[j]=min(dis2[j],dis2[k]+ma[j][k]);    
 94         
 95     
 96 
 97 
 98 int main()
 99 
100     int n,m,x;
101     scanf("%d %d %d",&n,&m,&x);
102     int a,b,c;
103     //因为要求的是最小时间,所以初始化为无穷
104     memset(ma,INF,sizeof(ma));
105     for(int i=1;i<=m;i++)
106     
107         scanf("%d %d %d",&a,&b,&c);
108         ma[a][b]=c;
109     
110     //回来的
111     dijkstra1(n,x);
112     //去的
113     dijkstra2(n,x);
114     int ans=0;
115     for(int i=1;i<=n;i++)
116     
117         //所有牛花费时间中最大的一个
118         ans=max(ans,dis1[i]+dis2[i]);
119     
120     printf("%d\n",ans);
121 

 

以上是关于Silver Cow Party POJ - 3268的主要内容,如果未能解决你的问题,请参考以下文章

POJ 3268 Silver Cow Party

POJ 3268 Silver Cow Party

poj 3268 Silver Cow Party

POJ 3268 Silver Cow Party (Dijkstra)

POJ 3268 Silver Cow Party

POJ3268 Silver Cow Party —— 最短路