链接:https://ac.nowcoder.com/acm/contest/904/D
来源:牛客网

DongDong坐飞机
时间限制:C/C++ 1秒,其他语言2秒
空间限制:C/C++ 524288K,其他语言1048576K
64bit IO Format: %lld
题目描述
愿时间过得慢一些,让我记住他的一颦一笑——DongDong

DongDong家的萨摩耶去国外读书了,DongDong非常想他,决定假期坐飞机去看望他,DongDong想合理使用手上的飞机折扣让自己不要吃土。给定n个城市,m条飞机航线,k次半价机会,1为DongDong家,n为萨摩耶家,每条单向边都有起点终点和机票价格(保证所有价格大于0),她可以k次使用半价折扣,求从1到n的最小花费。(若无法从1到n,输出-1)

输入描述:
第一行三个整数,n,m,k

接下来m行每行,u,v,w,表示存在u到v的边,代价为w(保证所有w均为偶数)

n<=10000,m<=50000,k<=10,0<=w<=1000000(w为偶数),数据可能有重边和自环
输出描述:
第一行输出最小花费
示例1
输入
复制
3 5 2
1 2 2
2 3 100
1 3 100
3 2 1010
1 3 1010
输出
复制
50

思路:
分层最短路的题目,可以定义二维数组dis[i][j] 表示1到第i节点,用了j次半价优惠,最短距离是多少?

容易知道 如果有一条边u指向v, 那么 dis[v][j] 可以由 dis[u][j] 和 dis[u][j-1] 转移过来。

在dijkstra的过程中维护dis[i][j] 即可。

理论复杂度O(nk log nk)

细节见代码:

#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <cmath>
#include <queue>
#include <stack>
#include <map>
#include <set>
#include <vector>
#include <iomanip>
#define ALL(x) (x).begin(), (x).end()
#define sz(a) int(a.size())
#define all(a) a.begin(), a.end()
#define rep(i,x,n) for(int i=x;i<n;i++)
#define repd(i,x,n) for(int i=x;i<=n;i++)
#define pii pair<int,int>
#define pll pair<long long ,long long>
#define gbtb ios::sync_with_stdio(false),cin.tie(0),cout.tie(0)
#define MS0(X) memset((X), 0, sizeof((X)))
#define MSC0(X) memset((X), '\0', sizeof((X)))
#define pb push_back
#define mp make_pair
#define fi first
#define se second
#define eps 1e-6
#define gg(x) getInt(&x)
#define chu(x) cout<<"["<<#x<<" "<<(x)<<"]"<<endl
using namespace std;
typedef long long ll;
ll gcd(ll a, ll b) {return b ? gcd(b, a % b) : a;}
ll lcm(ll a, ll b) {return a / gcd(a, b) * b;}
ll powmod(ll a, ll b, ll MOD) {ll ans = 1; while (b) {if (b % 2)ans = ans * a % MOD; a = a * a % MOD; b /= 2;} return ans;}
inline void getInt(int* p);
const int maxn = 10010;
const ll inf = 1e18;
/*** TEMPLATE CODE * * STARTS HERE ***/
struct node
{int to;int kk;ll val;node(){}node(int tt,int ww,ll vv){kk=ww;to=tt;val=vv;}bool operator < (const node & b) const{return val>b.val;}
};
std::vector<node> e[maxn];
ll dis[maxn][15];
void addedge(int a,int b,ll v)
{e[a].push_back(node(b,0,v));
}
void init(int n)
{for(int i=1;i<=n;++i){for(int j=0;j<=14;j++)dis[i][j]=inf;}
}
priority_queue<node> heap;
int n;
int m,k;
void dijkstra(int strat)
{init(n);dis[strat][0]=0ll;heap.push(node(strat,0,0ll));node temp;while(!heap.empty()){temp=heap.top();heap.pop();int now=temp.to;ll val=temp.val;int kk=temp.kk;if(kk>k){continue;}if(val>dis[now][kk])continue;for(auto x:e[now]){if(dis[x.to][kk]>val+x.val){dis[x.to][kk]=val+x.val;heap.push(node(x.to,kk,dis[x.to][temp.kk]));}if(kk<k&&dis[x.to][temp.kk+1]>val+x.val/2){dis[x.to][kk+1]=val+x.val/2;heap.push(node(x.to,kk+1,dis[x.to][temp.kk+1]));}}}
}
int main()
{//freopen("D:\\code\\text\\input.txt","r",stdin);//freopen("D:\\code\\text\\output.txt","w",stdout);gbtb;cin>>n>>m>>k;int u,v;ll c;while(m--){cin>>u>>v>>c;addedge(u,v,c);}dijkstra(1);ll ans=inf;repd(i,0,k){ans=min(ans,dis[n][i]);// printf("%lld ",dis[n][i] );}if(ans==inf)ans=-1;cout<<ans<<endl;return 0;
}inline void getInt(int* p) {char ch;do {ch = getchar();} while (ch == ' ' || ch == '\n');if (ch == '-') {*p = -(getchar() - '0');while ((ch = getchar()) >= '0' && ch <= '9') {*p = *p * 10 - ch + '0';}}else {*p = ch - '0';while ((ch = getchar()) >= '0' && ch <= '9') {*p = *p * 10 + ch - '0';}}
}

转载于:https://www.cnblogs.com/qieqiemin/p/11298508.html

牛客练习赛47 D DongDong坐飞机 (分层最短路)相关推荐

  1. 牛客挑战赛47 D Lots of Edges(最短路+递归枚举子集)

    牛客挑战赛47 D Lots of Edges 思路:点的权值最多只有(1<<17)-1(131071) ,那我们可以枚举终点的值来算最短路,每个点能连边的值都是固定的,可以通过递归枚举子 ...

  2. 牛客练习赛81 E. 小 Q 与函数求和 1( “简单莫比乌斯反演” ,欧拉函数性质)

    整理的算法模板合集: ACM模板 点我看算法全家桶系列!!! 实际上是一个全新的精炼模板整合计划 牛客练习赛81 E. 小 Q 与函数求和 1( "简单莫比乌斯反演" ) Prob ...

  3. 解题报告(一)C、(牛客练习赛41 F)简单数学题(数论 + FWT)(3.5)

    繁凡出品的全新系列:解题报告系列 -- 超高质量算法题单,配套我写的超高质量题解和代码,题目难度不一定按照题号排序,我会在每道题后面加上题目难度指数(1∼51 \sim 51∼5),以模板题难度 11 ...

  4. 牛客练习赛34 E little w and Digital Root(数位dp)

    title: 牛客练习赛34 E little w and Digital Root(数位dp) date: 2018-12-17 22:38:37 tags: 数位dp categories:ACM ...

  5. 牛客练习赛34 - C little w and Segment Coverage(思维、树状数组)

    title: 牛客练习赛34 - C little w and Segment Coverage(思维.树状数组) date: 2018-12-15 16:36:55 tags: [树状数组,思维] ...

  6. 牛客练习赛52 | C | [烹饪] (DP,裴蜀定理,gcd)

    牛客练习赛52 C 烹饪 链接:https://ac.nowcoder.com/acm/contest/1084/C来源:牛客网 时间限制:C/C++ 1秒,其他语言2秒 空间限制:C/C++ 327 ...

  7. 牛客练习赛73 D 离别(线段树+右端点排序离线查询)

    牛客练习赛73 D 离别 思路: 对于每一个固定的右端点i,我们都找到一个区间(l,r)使得区间中的点为左端点时 里面最大的的种数为k. 这个可以用队列或者vector来维护. 然后我们对于q个查询, ...

  8. 牛客练习赛75 D 减数游戏(队列优化(需要取模的)堆)

    牛客练习赛75 D 减数游戏 思路:写一下式子可以发每次选择最小的两个数进行操作,最后得到的答案会是最大的,那我们可以将它放进一个最小堆中来维护,但是里面的数是需要取模的,当它取模的时候,将会变小.那 ...

  9. 牛客挑战赛47 C 条件(Floyd bitset优化)

    牛客挑战赛47 C 条件 思路:首先我们要两个图,一个是一定能到达的,一个是可能到达的,如果我们使用floyd (n^3)就有可能会超时,因为只要求询问能否到达,所以权值只有0和1,那我们可以使用bi ...

  10. 牛客挑战赛47 A 一道GCD问题

    牛客挑战赛47 A 一道GCD问题 思路参考牛客上的题解: 根据多维的更相减损术得gcd(x,y,z)=gcd(x,y−x,z−y)得 gcd(a1+k,a2+k,a3+k-,an+k)=gcd(a1 ...

最新文章

  1. 函数参数传递常用的三种方式
  2. freemarker模板文件中文本域(textarea)的高度自适应实现
  3. linux系统中查看己设置iptables规则
  4. Django 的视图层
  5. 线性表的实现及其基本操作
  6. python try else_python try/except/else与递归
  7. 美国款游戏计算机,美国一程序员设计计算机游戏 悼念早逝爱子(图)
  8. 【leetcode 简单】 第三十五题 环形链表
  9. 媲美专业相机? 看看华为P40带来的影像新突破!
  10. 3d激光雷达开发(PassThrough滤波器)
  11. sas数字转日期格式_[转载]SAS日期格式输出格式大全
  12. paip.网站提示SESSION过期 登录过期 以及二次登录的问题
  13. Luogu5889 跳树
  14. 生成模型应用——使用变分自编码器(VAE)控制人脸属性生成人脸图片
  15. deepstream-test3
  16. C# OpenCv 证件照换底色
  17. php楼梯有n级台阶,楼梯问题的一些解决方法
  18. 在项目中怎样写故障树或者类层次
  19. 【GStreamer 】2-ubuntu v4l2-ctl 查看USB 相机基本参数
  20. 虚拟硬盘 服务器 破解,服务器版虚拟硬盘_Primo Ramdisk Server Edition V5.6.1 免费版

热门文章

  1. 计算机网络笔记2 应用层
  2. 500行代码,教你用python写个微信飞机大战
  3. 几个比较实用的网址链接
  4. 20常见的手机问题及其解决方案
  5. matlab中e如何输入,Matlab中表达e的操作方法介绍
  6. •检查你的代理设置127.0.0.1:2****。 转到“工具”“Internet 选项”“连接”。如果你在 LAN 中,请单击“局域网设置”。
  7. ORACLE11g数据库安装-刘建-专题视频课程
  8. 认识uclinux(与LINUX区别)
  9. NHibernate]集合类(Collections)映射
  10. c#网络通信框架networkcomms内核解析之六 处理接收到的二进制数据