本文首发于微信公众号:"算法与编程之美",欢迎关注,及时了解更多此系列文章。
前言
有一种算法叫“贪心”,“贪心”又可叫做“贪婪”,贪得的欲望,从字面意思上不难理解这种算法求解目的就是贪心的,为什么这么说,因为这种算法求解问题的实质就是每次的选择总是最优的,就好比去菜市场买菜或者买水果,在购买的时候,总是会挑选从自身角度来说最绿色,最新鲜的。
贪心算法便是这样的一个算法范例,但是就这样的一个算法求解出来的问题就是得到最优解了吗,当然并不是,这种算法它遵循的规则是在每个阶段做出局部的最优选择,并没有考虑全局的最优解答。
问题描述
在一条环路上有N个加油站,其中第i个加油站有汽油gas[i]升。
你有一辆油箱容量无限的的汽车,从第 i 个加油站开往第 i+1个加油站需要消耗汽油 cost[i] 升。你从其中的一个加油站出发,开始时油箱为空。
如果你可以绕环路行驶一周,则返回出发时加油站的编号,否则返回 -1。
示例1:
输入:gas = [1,2,3,4,5]
cost = [3,4,5,1,2]
输出:3
解释:从 3 号加油站(索引为 3 处)出发,可获得 4 升汽油。此时油箱有 = 0 + 4 = 4 升汽油
开往 4 号加油站,此时油箱有4 - 1 + 5 = 8 升汽油
开往 0 号加油站,此时油箱有8 - 2 + 1 = 7 升汽油
开往 1 号加油站,此时油箱有7 - 3 + 2 = 6 升汽油
开往 2 号加油站,此时油箱有6 - 4 + 3 = 5 升汽油
开往 3 号加油站,你需要消耗5 升汽油,正好足够你返回到 3 号加油站。
因此,3 可为起始索引。来源:力扣(LeetCode)
示例2:
输入:gas = [2,3,4]
cost = [3,4,3]
输出:-1
解释:你不能从0号或1号加油站出发,因为没有足够的汽油可以让你行驶到下一个加油站。
我们可以从2号加油站出发,可以获得4升汽油,此时油箱有0+4升油
开往0号加油站,此时油箱有4-3+2=3升油
开往1号加油站,此时有油箱3-3+3=3升油
你无法返回2号加油站因为需要4升油,因此,无论怎么样,都不能环绕行驶一周
来源:力扣(LeetCode)
解决方案
首先通过示例2可以知道,当所有加油站的汽油2+3+4=9升汽油小于消耗的汽油3+3+4=10升汽油时不能行驶一周,那么就有了第一个判断条件,当满足条件sum(gas)>sum(cost)时,便进行下一步的求解,很显然起始位置便是要得答案,但是怎么去判断这个起始位置的可行性呢,我们需要从第一个位置开始一一遍历,假如从一号加油站开往二号加油站耗油量小于加油量可以正常行驶,当从二号加油站开往三号加油站时,耗油量大于了加油量,就不能正常行驶,那么我们就又从二号加油站开始吗?其实不然,当出现二号加油站开往三号加油站油耗大于加油量时就已经证明开往三号之前所有的加油站都不能做为初始位置,因为三号之前的sum(gas)<sum(cost),那么我们之间油箱清零之间从三号加油站开始,继续如此计算便能得到答案。
结语
通过简单的示列问题解答可以了解到贪心算法基本原理以及思考问题的思路。
实习编辑:衡辉
稿件来源:深度学习与文旅应用实验室(DLETA)
转载:https://blog.csdn.net/gschen_cn/article/details/117538145