Recently, Shua Shua had a big quarrel with his GF. He is so upset that he decides to take a trip to some other city to avoid meeting her. He will travel only by air and he can go to any city if there exists a flight and it can help him reduce the total cost to the destination. There's a problem here: Shua Shua has a special credit card which can reduce half the price of a ticket ( i.e. 100 becomes 50, 99 becomes 49. The original and reduced price are both integers. ). But he can only use it once. He has no idea which flight he should choose to use the card to make the total cost least. Can you help him?

Input

There are no more than 10 test cases. Subsequent test cases are separated by a blank line.
The first line of each test case contains two integers N and M ( 2 <= N <= 100,000

0 <= M <= 500,000 ), representing the number of cities and flights. Each of the following M lines contains "X Y D" representing a flight from city X to city Y with ticket price D ( 1 <= D <= 100,000 ). Notice that not all of the cities will appear in the list! The last line contains "S E" representing the start and end city. X, Y, S, E are all strings consisting of at most 10 alphanumeric characters.

Output

One line for each test case the least money Shua Shua have to pay. If it's impossible for him to finish the trip, just output -1.

Sample Input

4 4
Harbin Beijing 500
Harbin Shanghai 1000
Beijing Chengdu 600
Shanghai Chengdu 400
Harbin Chengdu 4 0
Harbin Chengdu

Sample Output

800
-1

概译:共有N个城市,M行里给出某市到另一个市(单向)的机票价格(这M行未必包含所有的N个城市),然后给出起始点和终点。这期间可以有一次机票打折机会,求解最小花费。如果到达不了,输出-1。 思路:显然的图题。如果没有打折这一条件的话就是有向图的最短路径,而打折条件是典型的、在每一步操作中可选可不选的条件类型,dp处理一下。也就是我们在求解最短路的过程中加上几条dp思想的语句来记录所需结果,此处最短路用的是spfa。另外注意一下这个题中,点的给出形式为字符串,我用的是STL中的map对其进行转化处理。
代码如下:
 #include<cstdio>
#include<iostream>
#include<cstring>
#include<queue>
#include<map>
#include<vector>
#include<climits>
using namespace std; typedef long long ll;
const long long inf=LLONG_MAX; struct node
{
int id,cost;
node(int x,int y):id(x),cost(y){}
};
int n,m,cnt;//点数、边数、在输入里出现过的城市数
ll dis[][];//dp处理的距离
bool vis[];//spfa里负责记录是否在队列中
char ch1[],ch2[];//城市1,城市2
//以下为最短路所需容器
map<string,int>mp;
vector<node>v[];
queue<int>q; void spfa(int k)//求最短路
{
for(int i=;i<=n;i++)
dis[i][]=dis[i][]=inf;
dis[k][]=dis[k][]=;
//dis[i][0]代表到达i点时以前打过一次折的最小花费,即dis[城市2][0]就是结果,dis[i][1]是到达i点之前一直不打折的花费
memset(vis,false,sizeof(vis));
q.push(k);
while(!q.empty())
{
int t=q.front();q.pop();
vis[t]=false;
for(int i=;i<v[t].size();i++)
{
node e=v[t][i];
bool flag=false;
if(dis[e.id][]>dis[t][]+e.cost)//常规操作,把dis[i][1]当成模板里的dis[i]就行……
{
flag=true;
dis[e.id][]=dis[t][]+e.cost;
}
if(dis[e.id][]>dis[t][]+e.cost||dis[e.id][]>dis[t][]+e.cost/)
{//dp,之前打了折的花费加上这次的花费,与之前一直不打折这次打折的花费,取最小值为对于这个点的打过一次折以后的最小花费
flag=true;
dis[e.id][]=min(dis[t][]+e.cost,dis[t][]+e.cost/);
}
if(flag&&!vis[e.id])//更新了花费且此点不在队列中时
{
vis[e.id]=true;
q.push(e.id);
}
}
}
}
int main()
{
while(~scanf("%d%d",&n,&m))
{
//不要忘了各种清空
cnt=;
mp.clear();
for(int i=;i<=n;i++)
v[i].clear();
//建图
for(int i=;i<=m;i++)
{
int cost;//机票钱
scanf("%s%s%d",ch1,ch2,&cost);
//如果还没出现过这个城市,加进来,记录下来它的编号,简单起见第几个出现就是几了
if(!mp[ch1]) mp[ch1]=++cnt;
if(!mp[ch2]) mp[ch2]=++cnt;
v[mp[ch1]].push_back(node(mp[ch2],cost));//单向
}
scanf("%s%s",ch1,ch2);//起点终点
if(!mp[ch1]) mp[ch1]=++cnt;
if(!mp[ch2]) mp[ch2]=++cnt;
spfa(mp[ch1]);//求解
printf("%lld\n",dis[mp[ch2]][]==inf?-:dis[mp[ch2]][]);//inf代表无法到达
}
return ;
}
												

HDU-3499:Flight(SPFA+dp)的更多相关文章

  1. HDU 5236 Article(概率DP)

    http://acm.hdu.edu.cn/showproblem.php?pid=5236 题意:现在有人要在文本编辑器中输入n个字符,然而这个编辑器有点问题. 在i+0.1s(i>=0)的时 ...

  2. 【BZOJ】1003: [ZJOI2006]物流运输trans(SPFA+DP)

    http://www.lydsy.com/JudgeOnline/problem.php?id=1003 这题一开始看是不会的额,,,还是看题解了..一开始我觉得不能用最短路啥的,,看了题解发现这是d ...

  3. HDU 2571 命运 (简单DP)

    命运 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Submissi ...

  4. HDU - 3499 Flight 双向SPFA+枚举中间边

    Flight Recently, Shua Shua had a big quarrel with his GF. He is so upset that he decides to take a t ...

  5. PAT 甲级 1087 All Roads Lead to Rome(SPFA+DP)

    题目链接 All Roads Lead to Rome 题目大意:求符合题意(三关键字)的最短路.并且算出路程最短的路径有几条. 思路:求最短路并不难,SPFA即可,关键是求总路程最短的路径条数. 我 ...

  6. hdu 4625 Dice(概率DP)

    Dice Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others) Total Submi ...

  7. hdu 4826 Labyrinth(简单dp)

    Description 度度熊是一只喜欢探险的熊,一次偶然落进了一个m*n矩阵的迷宫,该迷宫只能从矩阵左上角第一个方格开始走,只有走到右上角的第一个格子才算走出迷宫,每一次只能走一格,且只能向上向下向 ...

  8. hdu 2571 命运(水DP)

    题意: M*N的grid,每个格上有一个整数. 小明从左上角(1,1)打算走到右下角(M,N). 每次可以向下走一格,或向右走一格,或向右走到当前所在列的倍数的列的位置上.即:若当前位置是(i,j), ...

  9. HDU 4745---Two Rabbits(区间DP)

    题目链接 http://acm.split.hdu.edu.cn/showproblem.php?pid=4745 题意:两只兔子,在n块围成一个环形的石头上跳跃,每块石头有一个权值ai,一只从左往右 ...

随机推荐

  1. 图解mysql join

    原文:http://www.codeproject.com/Articles/33052/Visual-Representation-of-SQL-Joins 这个图文解释mysql join的各种技 ...

  2. listen 56

    Kettles Stop Whistling in the Dark British physicist Lord Rayleigh is best known for his discovery o ...

  3. 学习 Shell —— 括号、引号

    shell中各种括号的作用().(()).[].[[]].{} shell中的括号(小括号,大括号/花括号) ${},大括号用于确定变量的范围: $(( 数学运算 )) 0. 引号 单引号.双引号.飘 ...

  4. ACM学习历程—ZOJ3471 Most Powerful(dp && 状态压缩 && 记忆化搜索 && 位运算)

    Description Recently, researchers on Mars have discovered N powerful atoms. All of them are differen ...

  5. 【LeetCode】064. Minimum Path Sum

    题目: Given a m x n grid filled with non-negative numbers, find a path from top left to bottom right w ...

  6. Eclipse常用配置(1)

    1.代码自动提示 在我们忘记方法名或者想偷懒时,代码自动提示很管用.不过Eclipse默认是输入"."后才会出现包或类成员的提示,也就意味着我们必须先输入一个完整的类名,提示才能出 ...

  7. 继承HibernateDaoSupport实现DAO(spring整合hibernate)

    转自:https://blog.csdn.net/yz9612/article/details/80234377 spring为hibernate的DAO提供工具类:HibernateDaoSuppo ...

  8. 转:isualvm远程监控Tomcat

    一.Java VisualVM 概述 对于使用命令行远程监控jvm 太麻烦 . 在jdk1.6 中 Oracle 提供了一个新的可视化的. JVM 监控工具 Java VisualVM .jvisua ...

  9. mysql连接错误解决

    EB101IWSWD-eyJsaWNlbnNlSWQiOiJFQjEwMUlXU1dEIiwibGljZW5zZWVOYW1lIjoibGFuIHl1IiwiYXNzaWduZWVOYW1lIjoiI ...

  10. vim跳转到文件的指定偏移位置

    :goto 偏移量 例如:偏移到文件的第100个字节处 :goto 100