代码随想录算法训练营第29天|134. 加油站、135. 分发糖果、860.柠檬水找零、406.根据身高重建队列

1.134. 加油站

题目链接:134. 加油站
文档讲解: 代码随想录

思路:如果 gas 的总和小于 cost 的总和,说明无论从哪里出发,肯定不能跑一圈。定义 rest 记录每天剩下的油,从0开始计算累加,如果遇到负数,则从下一个站点算起。

这道题的暴力解法,是用 for 遍历,用 while 模拟跑一圈的情况。

class Solution(object):
    def canCompleteCircuit(self, gas, cost):
        """
        :type gas: List[int]
        :type cost: List[int]
        :rtype: int
        """
        for i in range(len(gas)):
            rest = gas[i] - cost[i]
            index = (i + 1) % len(cost)
            while rest > 0 and index != i:
                rest += gas[index] - cost[index]
                index = (index + 1) %len(cost)
            if rest >= 0 and index == i:
                return i
        return -1
class Solution(object):
    def canCompleteCircuit(self, gas, cost):
        """
        :type gas: List[int]
        :type cost: List[int]
        :rtype: int
        """
        cur = 0
        tot = 0
        start = 0
        for i in range(len(gas)):
            cur += gas[i] - cost[i]
            tot += gas[i] - cost[i]
            if cur < 0:
                start = i + 1
                cur = 0
        if tot < 0:
            return -1 
        return start               

2.135. 分发糖果

题目链接:135. 分发糖果
文档讲解: 代码随想录

这道题一定要确定一边再确定另一边,两边同时考虑会顾此失彼。可以先比较右边评分大于左边的情况,从前往后遍历。只要右边评分比左边大,右边的孩子就多一个糖果,可以达到全局最优:相邻的孩子中,评分高的右孩子获得比左孩子更多的糖果。再从后往前遍历,比较左边评分高于后边的情况,两个糖果数量取较大值。

class Solution(object):
    def candy(self, ratings):
        """
        :type ratings: List[int]
        :rtype: int
        """
        candy = [1] * len(ratings)
        for i in range(1, len(ratings)):
            if ratings[i] > ratings[i - 1]:
                candy[i] = candy[i - 1] + 1
        for i in range(len(ratings) - 2, -1, -1):
            if ratings[i] > ratings[i + 1]:
                candy[i] = max(candy[i + 1] + 1, candy[i])
        summ = 0
        for i in range(len(candy)):
            summ += candy[i]
        return summ      

3.860.柠檬水找零

题目链接:860.柠檬水找零
文档讲解: 代码随想录

思路超级简单,根据收到的面额大小制定不同的找零策略。需要注意的是,对于20美元,优先使用一张10和一张5进行找零。

class Solution(object):
    def lemonadeChange(self, bills):
        """
        :type bills: List[int]
        :rtype: bool
        """
        five = 0
        ten = 0
        twenty = 0
        for i in range(len(bills)):
            if bills[i] == 5:
                five += 1
            if bills[i] == 10:
                five -= 1
                ten += 1
                if five < 0:
                    return False
            if bills[i] == 20:
                twenty += 1
                if ten > 0:
                    ten -= 1
                    five -= 1
                else:
                    five -= 3
                if ten < 0 or five < 0:
                    return False
        return True

4.406.根据身高重建队列

题目链接:406.根据身高重建队列
文档讲解: 代码随想录

思路:和分发糖果一样,不能同时考虑身高和 k,因此先按照身高降序排列,然后再根据 k 来调整队列。

class Solution(object):
    def reconstructQueue(self, people):
        """
        :type people: List[List[int]]
        :rtype: List[List[int]]
        """
        #根据身高降序排列,如果身高相同则k小的在前面
        people.sort(key = lambda x:(-x[0],x[1]))

        queue = []

        #根据每个元素的第二个元素进行插入
        for p in people:
            queue.insert(p[1],p)
        return queue
  • 3
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值