寒假到了,小明准备坐火车回老家,现在他从学校出发去火车站,CC市去火车站有两种方式:轻轨和公交车。小明为了省钱,准备主要以乘坐公交为主。CC市还有一项优惠政策,持学生证可以免费乘坐一站轻轨(但只能乘坐一站)。小明想尽快到达火车站,请编写程序为小明找到一条从学校到火车站最快的路线及换乘轻轨的方案。
假设换乘时间忽略不计,公交车与轻轨站点相同,但线路和速度不一定相同,所有线路都是双向的。可以第一站就乘坐轻轨,也可以最后一站乘坐轻轨,也可以在中间某站坐轻轨。如果乘坐轻轨和不乘坐轻轨到达火车站的时间相同,则无需换乘轻轨。最多坐一站轻轨。
输入格式:
输入包含多组数据。每组数据第一行为3个整数n、s和t,分别表示车站数(编号为1至n),小明学校所在的站和火车站所在的站。下一行为一个整数m,表示公交车的线路信息,接下来m行,每行为3个正整数a、b、c,表示公交车从a站到b站需要c分钟。下一行为一个整数k,表示轻轨的线路信息,接下来k行,每行为3个正整数x、y、z,表示轻轨从x站到y站需要z分钟。所有整数均不超过20000。
输出格式:
对每组数据输出2行。第1行为1个整数T,表示从学校到达火车站的最短时间;第2行为一个整数K,表示在站点K换乘轻轨,若有多个可能的换乘点,则输出编号最小者,如果无需换乘轻轨,则第二行输出“no metro”。
输入样例:
4 1 4
4
1 2 2
1 3 3
2 4 4
3 4 5
1
2 4 3
4 1 4
4
1 2 2
1 3 3
2 4 4
3 4 5
1
2 4 3
输出样例:
5
2
5
2
思路:
使用迪杰斯特拉模板算出起点,终点到所有点的最短路;
根据所有的车票(a<->b)计算(起点->a+轻轨时间+b->终点)/(起点->b+轻轨时间+a->终点)
如果小于ans(初值为起点到终点的时间),就改变他,并且改变way(在哪个点转站);
最后如果way的值未改变就输出“no metro”;
代码:
#include<bits/stdc++.h>
using namespace std;
#define ll long long
#define pii pair<int,int>
ll n , T , k , idx , sta , en;
const int l = 40005;
int ne[l] , e[l] , w[l] , h[l] , dist[l];
int d1[l] , d2[l];
bool st[l];
void bfs(int x){
memset(st,0,sizeof st);
memset(dist,0x3f,sizeof dist);
priority_queue<pii,vector<pii>,greater<pii> > q;
dist[x] = 0;
q.push({dist[x],x});
while(!q.empty()){
int t = q.top().second;
q.pop();
if(st[t])continue;
st[t] = 1;
for(int i = h[t] ; ~ i ; i = ne[i]){
int x = e[i];
if(dist[x] <= dist[t] + w[i])continue;
dist[x] = dist[t] + w[i];
q.push({dist[x],x});
}
}
}
void add(int a,int b,int c){
ne[idx] = h[a];
e[idx] = b;
w[idx] = c;
h[a] = idx ++;
}
int main(){
while(cin >> n >> sta >> en){
idx = 0;
memset(h , - 1 , sizeof h);
cin >> T;
while(T --){
int a , b , c;
cin >> a >> b >> c;
add(a,b,c);
add(b,a,c);
}
cin >> T;
bfs(sta);for(int i = 1 ; i <= n ; i ++)d1[i] = dist[i];
bfs(en );for(int i = 1 ; i <= n ; i ++)d2[i] = dist[i];
int ans = d1[en];
int way = 0;
while(T --){
int a , b , c;
cin >> a >> b >> c;
if(d1[a] + c + d2[b] < ans){
way = a;
ans = d1[a] + c + d2[b];
}
if(d1[b] + c + d2[a] < ans){
way = b;
ans = d1[b] + c + d2[a] ;
}
}
cout << ans << endl;
way ? cout << way << endl : cout << "no metro" << endl;
}
}