P4568 [JLOI2011]飞行路线
生活随笔
收集整理的這篇文章主要介紹了
P4568 [JLOI2011]飞行路线
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
P4568 [JLOI2011]飛行路線
Description
Alice和Bob現在要乘飛機旅行,他們選擇了一家相對便宜的航空公司。該航空公司一共在n個城市設有業務,設這些城市分別標記為0到n-1,一共有m種航線,每種航線連接兩個城市,并且航線有一定的價格。
Alice和Bob現在要從一個城市沿著航線到達另一個城市,途中可以進行轉機。航空公司對他們這次旅行也推出優惠,他們可以免費在最多kk種航線上搭乘飛機。那么Alice和Bob這次出行最少花費多少?
Input
- 數據的第一行有三個整數,n,m,k,分別表示城市數,航線數和免費乘坐次數。
第二行有兩個整數,s,t,分別表示他們出行的起點城市編號和終點城市編號。
接下來有m行,每行三個整數,a,b,c,表示存在一種航線,能從城市a到達城市b,或從城市b到達城市a,價格為c。
Output
- 只有一行,包含一個整數,為最少花費。
Sample Input
5 6 1
0 4
0 1 5
1 2 5
2 3 5
3 4 5
2 3 3
0 2 100
Sample Output
8
Data Size
- 對于100%的數據,2≤n≤10000,1≤m≤50000,0≤k≤10,0≤s,t<n,0≤a,b<n,a≠b,0≤c≤1000
題解:
- 分層圖最短路。
- 觀察數據范圍,k特別小(<=10)。所以可以用拆點的思想,就是把一個點拆成k種情況:用1次機會到達的、用2次機會到達的...用k次機會到達的。這樣所有的狀態就變成了一個大圖。在這個大圖上面跑最短路即可。
#include <iostream>
#include <cstdio>
#include <queue>
#include <cstring>
#define N 100005
#define M 1000005
using namespace std;struct Node
{int val, pos;friend bool operator < (Node x, Node y) {return x.val > y.val;}
};
struct E {int next, to, dis;} e[M];
int n, m, k, s, t, num, ans = 0x7fffffff;
int h[N], dis[N];
bool vis[N]; int read()
{int x = 0; char c = getchar();while(c < '0' || c > '9') c = getchar();while(c >= '0' && c <= '9') {x = x * 10 + c - '0'; c = getchar();}return x;
}void add(int u, int v, int w)
{e[++num].next = h[u];e[num].to = v;e[num].dis = w;h[u] = num;
}void dijskra()
{memset(dis, 0x3f, sizeof(dis));priority_queue<Node> que;dis[s] = 0, que.push((Node){0, s});while(!que.empty()){int x = que.top().pos; que.pop();if(vis[x]) continue;vis[x] = 1;for(int i = h[x]; i != 0; i = e[i].next)if(dis[x] + e[i].dis < dis[e[i].to]){dis[e[i].to] = dis[x] + e[i].dis;if(!vis[e[i].to]) que.push((Node){dis[e[i].to], e[i].to});}}
}int main()
{cin >> n >> m >> k >> s >> t;s++, t++;for(int i = 1; i <= m; i++){int u = read() + 1, v = read() + 1, w = read();add(u, v, w), add(v, u, w);for(int j = 1; j <= k; j++){add(u + j * n, v + j * n, w);add(v + j * n, u + j * n, w);add(u + (j - 1) * n, v + j * n, 0);add(v + (j - 1) * n, u + j * n, 0);}}dijskra();for(int i = 0; i <= k; i++)ans = min(ans, dis[t + i * n]);cout << ans; return 0;
}
轉載于:https://www.cnblogs.com/BigYellowDog/p/11216971.html
總結
以上是生活随笔為你收集整理的P4568 [JLOI2011]飞行路线的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 有没有小学语文老师来传授下学习方法,我家
- 下一篇: 扩展jquery实现客户端表格的分页、排