Day 29 - Leetcode 1005K次取反后最大化的数组和 | Leetcode 134加油站 | Leetcode 135分发糖果

文章介绍了在LeetCode上解决三个问题的策略,包括如何通过改变负数的顺序使数组和最大,找寻可以循环驾驶的起点,以及分配糖果以保证评分高的孩子得到更多。关键在于寻找局部和全局最优解,并提供了相应的Java代码实现。
摘要由CSDN通过智能技术生成

leetcode 1005

题目链接

思路

  • 局部最优:
    • 让绝对值大的负数变为正数,当前数值达到最大
  • 全局最优:
    • 整个数组和达到最大

注意:一定要以绝对值大小来进行排序!!具体 code 实现如下:

class Solution {
    public int largestSumAfterKNegations(int[] nums, int k) {
        nums = IntStream.of(nums)
		    .boxed()
		    .sorted((o1, o2) -> Math.abs(o2) - Math.abs(o1))
		    .mapToInt(Integer::intValue).toArray();
        for (int i = 0; i < nums.length; ++i) {
            if (nums[i] < 0 && k > 0) {
                nums[i] = 0 - nums[i];
                --k;
            }
        }
        if (k % 2 == 1)
            nums[nums.length - 1] = 0 - nums[nums.length - 1];
        int res = 0;
        for (int x : nums) 
            res += x;
        return res;
    }
}

leetcode 134

题目链接
找到一个可以循环开完车的起始位置

Input: gas = [1,2,3,4,5], cost = [3,4,5,1,2]
Output: 3
Explanation:
Start at station 3 (index 3) and fill up with 4 unit of gas. Your tank = 0 + 4 = 4
Travel to station 4. Your tank = 4 - 1 + 5 = 8
Travel to station 0. Your tank = 8 - 2 + 1 = 7
Travel to station 1. Your tank = 7 - 3 + 2 = 6
Travel to station 2. Your tank = 6 - 4 + 3 = 5
Travel to station 3. The cost is 5. Your gas is just enough to travel back to station 3.
Therefore, return 3 as the starting index.

思路

  • 定义rest[i] = gas[i] - cost[i]
  • i=0的位置开始,求0 ~ i的累计rest值sum
    • 如果sum < 0,说明该段区间内不可能存在startIndex, ∵ \because 一定会没油了
    • sum < 0的话,从i + 1的位置重新计算 sum
  • 局部最优:
    • 当前累加rest[i]的和curSum一旦小于0,起始位置至少要是i+1,因为从i之前开始一定不行
  • 全局最优:
    • 找到可以跑一圈的起始位置
class Solution {
    public int canCompleteCircuit(int[] gas, int[] cost) {
        int sum = 0;
        int total = 0;
        int res = 0;
        for (int i = 0; i < gas.length; ++i) {
            sum += gas[i] - cost[i];
            total += gas[i] - cost[i];
            if (sum < 0) {
                sum = 0;
                res = i + 1;
            }
        }
        if (total < 0)
            return -1;
        else
            return res;
    }
}

leetcode 135

题目链接
分糖果,相邻 higher rating 的孩子分更多candy

思路

  • 局部最优
    • 只要右边评分比左边大,右边的孩子就多一个糖果
  • 全局最优
    • 相邻的孩子中,评分高的右孩子获得比左边孩子更多的糖果
  • 遍历2遍,一次从前往后,一次从后往前
class Solution {
    public int candy(int[] ratings) {
        if (ratings.length == 1)
            return 1;
        int[] candyy = new int[ratings.length];
        for (int i = 0; i < ratings.length; ++i) {
            candyy[i] = 1;
            if (i != 0 && ratings[i] > ratings[i - 1])
                candyy[i] = candyy[i - 1] + 1;
        }
        for (int i = ratings.length - 1; i >= 0; --i) {
            if (i != ratings.length - 1 && ratings[i] > ratings[i + 1] && candyy[i] <= candyy[i + 1])
                candyy[i] = candyy[i + 1] + 1;
        }

        int res = 0;
        for (int x : candyy)
            res += x;
        return res;
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值