题意:有一张图,每条边有一个边权t表示经过所花时间,每个点有两个权t、p,分别表示经过该点所花时间和所花费用,要求找一条路径,从点1出发再回到点1,所花时间恰好为x且费用最小,输出其费用,找不到则输出“It is a trap.”

思路:这题的解法和之前一场网络赛碰到的L题异曲同工,那题的题意是有k次机会把一条路的边权置为0,求最短路。我们可以把它抽象成分层图,即用二维的dis数组,dis[i][j]表示到点i且状态为j的最小花费。具体到题目来说,就是到点i且剩下j次机会的最小花费。也就是说,一个点,可以选择用或不用“边权置0”操作,转移到它连接的下一个点,相当于转移出两个状态。

而回到这一题,我们定义dis[i][j]表示到点i且还剩下j时间要走状态下的最小花费,由于这题可以在一个点一直停留,所以dis[u][x]可以转移到dis[u][x-u.t]和dis[v][x-w-v.t]。

这题加深了我对dijkstra最短路的理解。跑dij的过程其实可以看成DP的过程。和传统的最短路相比,可以理解为它一个点转移到其他点的状态变多了。思想大概如此,具体实现见代码

#include<iostream>
#include<cstdio>
#include<vector>
#include<queue>
#include<map>
#include<algorithm>
#include<cstring>
#include<string>
#include<cmath>
#include<set>
#include<functional>
#include<climits>
#include<cstdlib>
#include<climits>
#define mp make_pair
#define pb push_back
#define fi first
#define se second
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
#define de(x) cout<<#x<<" = "<<x<<endl
#define dd(x) cout<<#x<<" = "<<x<<" "
#define Clear(x,y) memset(x,y,sizeof(x))
using namespace std;
typedef long long ll;
typedef long double ld;
typedef pair<int,int> P;
typedef vector<int> V;
typedef map<int,int> M;
typedef set<int> S;
typedef queue<int> Q;
typedef priority_queue<int> BQ;
typedef set<int> S;
const double eps=1e-8,pi=acos(-1);
const int maxn=5e3+100,mod=1e9+7,INF=0x3f3f3f3f;
struct node
{
int u,x,d;
node(int a,int b,int c):u(a),x(b),d(c){}
bool operator > (const node& no) const
{
return d>no.d;
}
};
typedef priority_queue<node,vector<node>,greater<node> > SQ;
P edge[maxn],vec[maxn];
bool vis[maxn][maxn];
int dis[maxn][maxn],head[maxn],cnt;
void add(int u,int v)
{
edge[++cnt].se=head[u];
edge[cnt].fi=v;
head[u]=cnt;
}
void dij(int s,int x,int w)
{
Clear(dis,INF);
SQ q;
if (x-vec[s].fi<0)
return;
dis[s][x-vec[s].fi]=vec[s].se;
q.push(node(s,x-vec[s].fi,vec[s].se));
while (!q.empty())
{
node p=q.top();
q.pop();
int u=p.u,x=p.x,d=p.d;
if (vis[u][x])
continue;
vis[u][x]=1;
if (x-vec[u].fi>=0&&dis[u][x] + vec[u].se < dis[u][x-vec[u].fi])
{
dis[u][x-vec[u].fi] = dis[u][x] + vec[u].se;
q.push(node(u, x-vec[u].fi, dis[u][x-vec[u].fi]));
}
for (int i=head[u];i;i=edge[i].se)
{
int v=edge[i].fi;
if (x - vec[v].fi - w >= 0 && dis[u][x] + vec[v].se < dis[v][x-vec[v].fi-w])
{
dis[v][x-vec[v].fi-w] = dis[u][x] + vec[v].se;
q.push(node(v, x-vec[v].fi-w, dis[v][x-vec[v].fi-w]));
}
}
}
}
int main()
{
int n,m,x,w;
scanf("%d%d%d%d",&x,&n,&m,&w);
for (int i=0;i<m;++i)
{
int u,v;
scanf("%d%d",&u,&v);
add(u,v);
add(v,u);
}
for (int i=1;i<=n;++i)
scanf("%d%d",&vec[i].fi,&vec[i].se);
dij(1,x,w);
if (dis[1][0]==INF)
printf("It is a trap.");
else
printf("%d",dis[1][0]);
return 0;
}

Codeforces Gym Joyride(分层图,dijkstra)的更多相关文章

  1. [USACO09FEB] Revamping Trails 【分层图+Dijkstra】

    任意门:https://www.luogu.org/problemnew/show/P2939 Revamping Trails 题目描述 Farmer John dutifully checks o ...

  2. 【BZOJ-3627】路径规划 分层图 + Dijkstra + spfa

    3627: [JLOI2014]路径规划 Time Limit: 30 Sec  Memory Limit: 128 MBSubmit: 186  Solved: 70[Submit][Status] ...

  3. bzoj 1579: [Usaco2009 Feb]Revamping Trails 道路升级——分层图+dijkstra

    Description 每天,农夫John需要经过一些道路去检查牛棚N里面的牛. 农场上有M(1<=M<=50,000)条双向泥土道路,编号为1..M. 道路i连接牛棚P1_i和P2_i ...

  4. HDU-3499Flight (分层图dijkstra)

    一开始想的并查集(我一定是脑子坏掉了),晚上听学姐讲题才知道就是dijkstra两层: 题意:有一次机会能使一条边的权值变为原来的一半,询问从s到e的最短路. 将dis数组开成二维,第一维表示从源点到 ...

  5. bzoj1922 [SDOI2010]大陆争霸 分层图

    问题描述 幻想历8012年5月12日深夜,斯普林·布拉泽降下神谕:“Trust me, earn eternal life.”克里斯军团士气大增.作为克里斯军团的主帅,你决定利用这一机会发动奇袭,一举 ...

  6. Bzoj 2834: 回家的路 dijkstra,堆优化,分层图,最短路

    2834: 回家的路 Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 62  Solved: 38[Submit][Status][Discuss] D ...

  7. Bzoj 2662: [BeiJing wc2012]冻结 dijkstra,堆,分层图,最短路

    2662: [BeiJing wc2012]冻结 Time Limit: 3 Sec  Memory Limit: 128 MBSubmit: 647  Solved: 348[Submit][Sta ...

  8. Bzoj 1579: [Usaco2009 Feb]Revamping Trails 道路升级 dijkstra,堆,分层图

    1579: [Usaco2009 Feb]Revamping Trails 道路升级 Time Limit: 10 Sec  Memory Limit: 64 MBSubmit: 1573  Solv ...

  9. hdu 3499 flight 【分层图】+【Dijkstra】

    <题目链接> 题目大意: 现在给你一些点,这些点之间存在一些有向边,每条边都有对应的边权,有一次机会能够使某条边的边权变为原来的1/2,求从起点到终点的最短距离. 解题分析: 分层图最短路 ...

随机推荐

  1. Java-this关键词

    this关键词 1,this调用本类属性 在程序里面是有this可以实现以下三类的结构的描述: ·当前类中的属性:this.属性: ·当前类中的方法(普通方法.构造方法):this().this.方法 ...

  2. C#面向对象17 23种设计模式

    1.简单工厂模式 using System; using System.Collections.Generic; using System.Linq; using System.Text; using ...

  3. c# winfrom 界面设计

    1.在用DotnetBar的RibbonControl时,界面最大化时,会把电脑桌面的任务栏遮盖住: 解决办法:在load事件中写入: , Screen.PrimaryScreen.WorkingAr ...

  4. Makefile速查笔记

    Makefile速查笔记 Makefile中的几个调试方法 一. 使用 info/warning/error 增加调试信息 a. $(info "some text")打印 &qu ...

  5. 05 正确运行一个Go程序

    Go代码文件,程序中必须指定启动函数main() Hello.go package main //声明为main包,即可以编译成二进制程序 import "fmt" //导入fmt ...

  6. Apache Shiro漏洞复现

    利用burp dns进行检测,脚本如下: import sys import uuid import base64 import subprocess from Crypto.Cipher impor ...

  7. JDBC及PreparedStatement防SQL注入

    概述 JDBC在我们学习J2EE的时候已经接触到了,但是仅是照搬步骤书写,其中的PreparedStatement防sql注入原理也是一知半解,然后就想回头查资料及敲测试代码探索一下.再有就是我们在项 ...

  8. 【转】(深入理解计算机系统) bss段,data段、text段、堆(heap)和栈(stack)

    bss段: bss段(bss segment)通常是指用来存放程序中未初始化的全局变量的一块内存区域. bss是英文Block Started by Symbol的简称. bss段属于静态内存分配. ...

  9. js动态的往表格中加入表单元素

    效果如图: 这里我用的是layui的静态表格,其他框架也是一样的(只要你都表单元素要通过js进行渲染),我的需求是在表单中放了表格的元素,表格中还有表单的元素.表格中的行数据是js动态添加的,正常的添 ...

  10. 小程序UI设计(7)-布局分解-左-上下结构

    FlexBox布局中的变幻方式很多,我们继续了解一个左-上下结构的布局分解  左边结构树中WViewRow下面有两个WViewColumn.WViewRow是横向排列,WViewColumn是纵向排列 ...