NC25558. 西湖奇遇记Ⅰ
描述
鸡尾酒在去西湖的路上遇到了两个可爱的妹子,妹子邀请他一起逛西湖。但是西湖周边的景点太多了,还有许多道路让人眼花缭乱。初始鸡尾酒和妹子在第1个景点,妹子的目标是第N个景点。其中一些景点间有双向道路连接,也有一些景点间没有路,经过每条路都要消耗一定的时间。鸡尾酒不在意中间这些景点,他只想最快的领妹子到第N的景点。他带的钱可以带他和妹子乘坐k次观光车,观光车可以使他从某一个景点到另一个景点的时间消耗变为1(前提是两个景点间有直达的道路)
求鸡尾酒从点1走到点N的最短时间。
输入描述
输入第一行给两个正整数N,M, K(1<=N,M<=1e5,1<=k<=5)代表有N个点,M条路径,可以乘坐k次观光车
接下来M行,每行给出三个整数a b c,代表a b两点间有一条路,需要时间c才能通过。(1<=a,b <= N, 1<=c <= 1e9)
输出描述
输出一行一个整数表示答案
示例1
输入:
3 3 1 1 2 3 2 3 3 1 3 100
输出:
1
说明:
可以乘坐1次观光车,直接从1到3,消耗时间为1C++11(clang++ 3.9) 解法, 执行用时: 1127ms, 内存消耗: 30688K, 提交时间: 2019-05-11 16:09:24
#include<bits/stdc++.h> using namespace std; using LL = long long; constexpr int maxn = 2e5; constexpr int maxk = 7; vector<pair<int, LL> > G[maxn]; LL d[maxn * maxk]; bool done[maxn * maxk]; priority_queue<pair<LL, int>, vector<pair<LL, int>>, greater<pair<LL, int>>> q; int main(){ ios::sync_with_stdio(false); cin.tie(nullptr); cout.tie(nullptr); int n, m, k; cin >> n >> m >> k; for(int i = 1; i <= m; i += 1){ int a, b, c; cin >> a >> b >> c; a -= 1, b -= 1; G[a].push_back(make_pair(b, c)); G[b].push_back(make_pair(a, c)); } fill(d, d + maxn * maxk, 1e18); q.push({d[0] = 0, 0}); while(not q.empty()){ int u = q.top().second; q.pop(); if(done[u]) continue; done[u] = true; for(const auto &p : G[u % n]){ int v = p.first + u / n * n, w = p.second; if(d[v] > d[u] + w) q.push({d[v] = d[u] + w, v}); } if(u / n < k) for(const auto &p : G[u % n]){ int v = p.first + u / n * n + n; if(d[v] > d[u] + 1) q.push({d[v] = d[u] + 1, v}); } } LL ans = 1e18; for(int j = 0; j <= k; j += 1) ans = min(ans, d[j * n + n - 1]); cout << ans; return 0; }
C++14(g++5.4) 解法, 执行用时: 527ms, 内存消耗: 49204K, 提交时间: 2019-11-10 16:39:18
#include<bits/stdc++.h> using namespace std; const int N=1e6+100; #define ll long long int n,m,k; struct node { int v,w; }; vector<node>G[N]; struct node1 { int v,k; ll w; bool operator<(const node1&p) const { return w>p.w; }; } ; ll d[N][10]; ll dfs() { priority_queue<node1>q; while(q.size())q.pop(); for(int i=1;i<=n;i++) for(int j=0;j<=k;j++) d[i][j]=0x3f3f3f3f3f3f3f3f; q.push({1,0,0}); d[1][0]=0; while(q.size()) { node1 t=q.top(); q.pop(); int u=t.v; if(t.v==n) return t.w; for(int i=0;i<G[u].size();i++) { int v=G[u][i].v; int w=G[u][i].w; if(d[v][t.k]>d[u][t.k]+w) { d[v][t.k]=d[u][t.k]+w; q.push({v,t.k,d[v][t.k]}); } if(t.k+1<=k) { if(d[v][t.k+1]>d[u][t.k]+1) { d[v][t.k+1]=d[u][t.k]+1; q.push({v,t.k+1,d[v][t.k+1]}); } } } } } int main() { cin>>n>>m>>k; for(int i=1;i<=m;i++) { int x,y,w; cin>>x>>y>>w; G[x].push_back({y,w}); G[y].push_back({x,w}); } cout<<dfs()<<endl; return 0; }