codeUp 2031 To fill or not to fill 复杂贪心

2031: To Fill or Not to Fill

时间限制: 1 Sec  内存限制: 32 MB
提交: 599  解决: 132
With highways available, driving a car from Hangzhou to any other city is easy. But since the tank capacity of a car is limited, we have to find gas stations on the way from time to time. Different gas station may give different price. You are asked to carefully design the cheapest route to go.

Input Specification:

Each input file contains one test case. For each case, the first line contains 4 positive numbers: Cmax (<= 100), the maximum capacity of the tank; D (<=30000), the distance between Hangzhou and the destination city; Davg (<=20), the average distance per unit gas that the car can run; and N (<= 500), the total number of gas stations. Then N lines follow, each contains a pair of non-negative numbers: Pi, the unit gas price, and Di (<=D), the distance between this station and Hangzhou, for i=1,...N. All the numbers in a line are separated by a space.

Output Specification:

For each test case, print the cheapest price in a line, accurate up to 2 decimal places. It is assumed that the tank is empty at the beginning. If it is impossible to reach the destination, print "The maximum travel distance = X" where X is the maximum possible distance the car can run, accurate up to 2 decimal places.

Sample Input 1:
50 1300 12 8
6.00 1250
7.00 600
7.00 150
7.10 0
7.20 200
7.50 400
7.30 1000
6.85 300
Sample Output 1:
749.17
Sample Input 2:
50 1300 12 2
7.10 0
7.00 600
Sample Output 2:
The maximum travel distance = 1200.00
 

题意就是从起点到终点有很多的加油站 每个加油站有距离起点的距离和单价 我们从起点开车到终点 开始油量为0 要尽可能走到终点 问所求的最小花费是多少?如果走不到终点 就输出最远距离。

一开始给出油箱大小,到终点的距离,还有每单价油可以走的里程数,以及加油站的信息

 

分析:

由于这个问题逻辑比较复杂 可以先研究样例

假设汽车从起点S到终点E必须通过加一次油到达 可达范围内有多个价格不一的加油站 

如果可达范围内有更便宜的G 我们要选择那个加油站续命 先加够到这个加油站G的油 在到G处加新的油 这样就相当于从起点到G再到终点的松弛 可以通过这个加油站把后面的路程的花费给减小“松弛”掉  

如果选择某个并不是选择可达范围内最靠前的更便宜的加油站去加油站

如果选择了一个较远的,花费更大的站A 那么就必然导致起点加油变多花费变多,从A站新加的油到终点的这段距离花费变多 虽然路程变小 从全局来看 两种不同的选择花费不同的路段里 第二段从G到A花费变多 从A到终点E花费也变多 从而导致全局花费更大

如果选择了一个较近的花费更大的站B 那么从起点S到B花费不变 那么从B到G花费变多 从G到终点花费也变多  从而导致全局更大的花费

所以在当前站 选择可达范围内最近的且更便宜的能够带来更小的局部最优 从而获得更小的全局花费

如果没有更便宜的 

那么就要在初始S加满 这样才能尽可能少加更贵的油 从而减小花费

那么选择所有比初始S贵的里面最便宜G的  那么从S到G花费起点S的油钱 从G到终点E 再化一部分新加的G站油钱 如果不是这样选 得到的花费只会更大 怎么呢?

我们来看 这种情况下 续命油的油量是确定的 因为我前面加满了 

如果选择一个更近的站A但并不是可选加油站中最便宜的 那么从起点S到A花费不变,从A到G花费不变 但到终点需要加一次油 这时需要加的油会更贵一点(A站油钱) 从而全局花费更大

如果选择一个更远的站B但并不是可选加油站中最便宜的 那么起点到G花费不变 G到B花费不变 B到终点E 需要续一次油 花费变大(B站油钱)

所以在这种 分支下 我们也要选择贵中最便宜的那个去加油 从而获得全局最优

我们要找的续命的加油站 必须是可达范围里最便宜的 只有这样 才能通过这个最便宜的加油站 获取尽可能便宜的局部最优花费 这样再去选 

你有可能会有疑问

如果我们想G走着走着发现一个可达范围内更便宜站P的怎么办 即便如此 我们也要先到G站 看看能不能不加油直接走到P站 不过不可能! 因为P是G站决策之前的可达范围之外的站 必然不可能不加油走到P站 所以我们有必要中间续油 那么续油的话 只能在G续油 因为G是最相对便宜的 我们只有先到了G再看看需要续多少油到更便宜的加油站去 如果没有更便宜的加油站 则继续选择可达范围内所有更贵的里面最便宜的  所以整个过程就是

局部最优+局部最优+...+局部最优 = 全局最优

 

于是这个问题的逻辑大致就是如此 对每个加油站执行相同的逻辑 我们发现这样的话就是贪心策略 每到一个加油站 在能到达的范围内选择局部最优策略 这样走下来就能得到全局最优策略 如果在加油站不进行局部最优的策略 那么就必然导致花费变大

如果起始点没有加油站 那么就输出0 因为加不到油必然走不出去

否则:

看看加满油的话 能到达的范围内 有没有加油站 

                     如果没有 那么就加满油尽可能跑 能跑多远就输出多远

                     如果有加油站 看看有没有一个加油站是他能到达的范围内且离当前点比较近的?我们设此站位G站

                                 如果有 我们就买刚好到G站的油量:因为到了G站买油可以得到更便宜的价格 从而尽可能的得到更小的花费                                 如果没有 全都是比当前站更贵的加油站 那么就要从贵中选一个最便宜的设为H站 我们要走到那里继续买油才能尽可能的减小花费 注意 这时要从当前站加满油 因为H站的油是更贵的 但是又不能因为油贵而不走 还是要尽可能往前走的 这时如果不从H站买 从其他站买 只会导致更多的花费  所以我们要尽可能少的从H站买油 我们到了H站要站在H站的位置考虑更优的花费时 再从H站买油 故从当前站要加满油 然后去向H站   

 

由于本题需要维护的参数比较多 逻辑比较复杂 还是要想清楚逻辑后 把变量写的可读性高点 才能少出bug

时间复杂度:O(n^(所能到达的范围中的加油站个数))<O(n^2)<1000ms

 

#include<cstdio>
#include<cstring>
#include<iostream>
#include<map>
#include<cmath>
#include<algorithm>
#include<set>
#include<vector>
#include<climits>
#define Equal(a,b) (fabs((a)-(b))<=eps)
#define LessEqu(a,b) (((a)-(b))<=eps)
#define Lessthan(a,b) (((a)-(b))<-eps)
#define Morethan(a,b) (((a)-(b))>=eps)
#define MoreEqu(a,b) (((a)-(b))>=-eps)
const double eps = 1e-5;
using namespace std;
typedef long long ll;
struct station{double cost;double dis;
}S[510];
bool cmp(station a,station b){return Lessthan(a.dis,b.dis);
}
int main(){double c,dis,avg;int sta;ios::sync_with_stdio(0);cin>>c>>dis>>avg>>sta;for(int i=1;i<=sta;i++){cin>>S[i].cost>>S[i].dis;}double Lowest = S[1].cost;for(int i=2;i<=sta;i++){if(Lessthan(S[i].cost,Lowest)){Lowest = S[i].cost;}}sort(S+1,S+1+sta,cmp);if(!Equal(S[1].dis,0.0)){cout<<"The maximum travel distance = 0.00"<<endl;return 0;}bool f=0;S[sta+1].cost = 0,S[sta+1].dis = dis;double exp=0,canadd=c,distans=0,cut=0,unit=c;double costoil,oil = 0;bool fal = 0;for(int i=1;i<sta+1;i++){oil = (distans-S[i].dis)/avg;double Maxlim = S[i].dis + c*avg;double CMP = S[i].cost;int j,u=i;for(j=i+1;j<=sta+1&&LessEqu(S[j].dis,Maxlim);j++){if(Lessthan(S[j].cost,CMP)){CMP = S[j].cost;u = j;break;}}if(u==i&&j==i+1){//后面没加油站distans = Maxlim;fal = 1;break;}if(u!=i){//有个更便宜的unit = (S[u].dis-distans)/avg;//减去的是什么很关键exp+=S[i].cost*unit;// canadd = unit;distans = S[u].dis;i = u-1;oil += unit;costoil = unit;continue;}//如果后面的都是比自己贵的CMP = S[i+1].cost;u = i+1;for(int j=i+2;j<=sta+1&&LessEqu(S[j].dis,Maxlim);j++){if(LessEqu(S[j].cost,CMP)){//尽可能少买 也就是尽可能远CMP = S[j].cost;u = j;}}canadd = c-oil;distans += (canadd)*avg;exp+=canadd*S[i].cost;costoil = (S[u].dis-S[i].dis)/avg;oil=c;i = u-1;}if(fal)printf("The maximum travel distance = %.2f\n",distans);else printf("%.2f\n",round(exp*100)/100);return 0;
}

 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/425091.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

RabbitMQ(1) - win+rabbitMQ

rabbitMQ是一个在AMQP协议标准基础上完整的&#xff0c;可服用的企业消息系统。它遵循Mozilla Public License开源协议&#xff0c;采用 Erlang 实现的工业级的消息队列(MQ)服务器&#xff0c;Rabbit MQ 是建立在Erlang OTP平台上。 1.安装Erlang 所以在安装rabbitMQ之前&…

[周赛][Leetcode][第5457题][JAVA][动态规划][和为奇数的子数组数目]

【问题描述】5457. 和为奇数的子数组数目[中等] 【解答思路】 1. 动态规划 第 1 步&#xff1a;设计状态 dp[i][0] 记录以arr[i]结尾的和为奇数数量 dp[i][1] 记录以arr[i]结尾的和为偶数数量 第 2 步&#xff1a;状态转移方程 for(int i1;i<n;i){if(arr[i]%20){dp[i][0]…

第九期: 阿里巴巴程序员常用的15款开发者工具

阿里巴巴将自身在各类业务场景下的技术积淀&#xff0c;通过开源、云上实现或工具等形式对外开放&#xff0c;本文将精选了一些阿里巴巴的开发者工具&#xff0c;希望能帮助开发者们提高开发效率、更优雅的写代码。 从人工到自动化&#xff0c;从重复到创新&#xff0c;技术演进…

WPF 绑定StaticResource到控件的方法

WPF 绑定StaticResource到控件的方法 原文:WPF 绑定StaticResource到控件的方法资源文件内的属性能否直接通过绑定应用到控件&#xff1f;答案是肯定的。 比如&#xff0c;我们要直接把下面的<SolidColorBrush x:Key"RedBrush" Color"#FFFF0000" />直…

第三十三期:对于人工智能的恐惧及其5个解决方法

实施人工智能技术的IT领导人可能会感到一些恐惧&#xff0c;这有着充分的理由。人工智能在拥有数十年发展和应用历史的同时却有着奇怪的定位&#xff0c;但对于许多人来说&#xff0c;人工智能仍然是一种未来主义的感觉。 实施人工智能技术的IT领导人可能会感到一些恐惧&#x…

[Leetcode][第392题][JAVA][判断子序列][动态规划][双指针]

【问题描述】[简单] 【解答思路】 1. 双指针 时间复杂度&#xff1a;O(NM) 空间复杂度&#xff1a;O(1) class Solution { public:bool isSubsequence(string s, string t) {int n s.length(), m t.length();int i 0, j 0;while (i < n && j < m) {if (s[…

codeUp 2143: 迷瘴 浮点计算|贪心

2143: 迷瘴 时间限制: 1 Sec 内存限制: 32 MB 提交: 666 解决: 201 [提交][状态][讨论版][命题人:外部导入] 题目描述 小明正在玩游戏&#xff0c;他控制的角色正面临着幽谷的考验—— 幽谷周围瘴气弥漫&#xff0c;静的可怕&#xff0c;隐约可见地上堆满了骷髅。由于此处长…

权限分配之权限的展示

最后就是权限的展示了&#xff1a;对前面的 总结&#xff1a;  1. 一级菜单列表&#xff0c;是我对 menu表的&#xff0c;增删改查。  2. 二级菜单列表&#xff0c;是我对Permission表中&#xff0c; 可以作为二级菜单存在&#xff0c;如 客户列表、账单列表的 增删改查  …

优先队列----堆

问题 打印机打印作业一般是放在队列中的。如果按照先来先打印的顺序&#xff0c;有一个100页的打印任务&#xff0c;那么会让后面短小的任务等待很长时间。更合理的做法也许是最后处理最耗时的打印任务&#xff0c;不管它是不是最后提交上来的。 在多用户操作系统中&#xff…

第三十四期:游戏开发中常见的10种编程语言

游戏开发是非常有经验和熟练的程序员的工作。 它可能花费数亿美元。 这是一项非常有创意的工作&#xff0c;也需要技术水平。 他们需要具有特定需求的编程语言。 游戏开发是非常有经验和熟练的程序员的工作。 它可能花费数亿美元。 这是一项非常有创意的工作&#xff0c;也需要…

[Leetcode][第5458题][JAVA][字符串的好分割数目][双指针][HashSet]

【问题描述】5458. 字符串的好分割数目[中等] 【解答思路】 1. 双指针 前面的搜索前面的个数和&#xff0c;后面的搜索后面的个数和 时间复杂度&#xff1a;O(N^2) 空间复杂度&#xff1a;O(1) class Solution {/*双指针做法&#xff0c;前面的搜索前面的个数和&#xff0c;…

Spring Aop——给Advice传递参数

给Advice传递参数 Advice除了可以接收JoinPoint&#xff08;非Around Advice&#xff09;或ProceedingJoinPoint&#xff08;Around Advice&#xff09;参数外&#xff0c;还可以直接接收与切入点方法执行有关的对象&#xff0c;比如切入点方法参数、切入点目标对象&#xff08…

第三十五期:AI核心难点之一:情感分析的常见类型与挑战

情感分析或情感人工智能&#xff0c;在商业应用中通常被称为意见挖掘&#xff0c;是自然语言处理(NLP)的一个非常流行的应用。文本处理是该技术最大的分支&#xff0c;但并不是唯一的分支。情绪AI有三种类型及其组合。 情感分析或情感人工智能&#xff0c;在商业应用中通常被称…

AtCoder - 4172 Modulo Summation 贪心

开始想复杂的了 仔细观察样例后发现这个数 其实就是所有的数的LCM-1吗 只有LCM-1 对所有数取模的时候才能对所有数得到MOD = a[i]-1; 那么一个X%Y得到的最大值就是Y-1 于是得到了这个代码 #include<iostream> #include<cstdio> #include<queue> #includ…

[Leetcode][第104题][JAVA][二叉树的最大深度][递归][BFS]

【问题描述】[简单] 【解答思路】 1. 递归 终止条件/基本情况 root null 递推关系 max(l,r)1 时间复杂度&#xff1a;O(N) 空间复杂度&#xff1a;O(height) class Solution {public int maxDepth(TreeNode root) {if (root null) {return 0;} else {int leftHeight ma…

第三十六期:人工智能统计调查:86%的消费者更喜欢人工客服

美国消费者越来越不愿意与聊天机器人聊天&#xff0c;人们对人工智能作为关键业务组成部分的期望越来越高&#xff0c;由于部署这项新技术导致员工技能差距越来越大。 最近一些人工智能的健康和进展状况相关调查、研究、预测和其他定量评估突显出以下几点&#xff1a;美国消费者…

[Leetcode][第111题][JAVA][BFS][二叉树的最小深度][BFS][递归]

【问题描述】[简单] 【解答思路】 1. 递归 自下而上 基本情况/结束条件 &#xff1a; 叶子节点的定义是左孩子和右孩子都为 null 时叫做叶子节点 当 root 节点左右孩子都为空时&#xff0c;返回 1 当 root 节点左右孩子有一个为空时&#xff0c;返回不为空的孩子节点的深度 当…

PAT 1009 说反话

#include<cstdio>#include<cstring>#include<iostream>using namespace std;typedef long long ll;char a[82][82];int cnt;int main(){while(scanf("%s",a[cnt])!EOF){cnt;//***** 由于这里把cnt放到上面的判断中去了导致 最后在判断EOF的时候多判…

75 jsp基础语法汇总

JSP语法 脚本程序 脚本程序可以包含任意量量的Java语句句、变量量、⽅方法或表达式&#xff0c;只要它们在脚本语⾔言 中是有效的。 脚本程序的语法格式&#xff1a; <% 代码⽚片段 %>或者&#xff0c;您也可以编写与其等价的XML语句句&#xff0c;就像下⾯面这样&#…