当前位置: 首页 > news >正文

代码随想录算法训练营第三十四天-贪心算法3| 1005.K次取反后最大化的数组和 134. 加油站 135. 分发糖果

1005. Maximize Sum Of Array After K Negations

参考视频:贪心算法,这不就是常识?还能叫贪心?LeetCode:1005.K次取反后最大化的数组和_哔哩哔哩_bilibili 

贪心🔍

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

局部最优可以推出全局最优。

那么如果将负数都转变为正数了,K依然大于0,此时的问题是一个有序正整数序列,如何转变K次正负,让 数组和 达到最大。

那么又是一个贪心:局部最优:只找数值最小的正整数进行反转,当前数值和可以达到最大(例如正整数数组{5, 3, 1},反转1 得到-1 比 反转5得到的-5 大多了),全局最优:整个 数组和 达到最大。

虽然这道题目大家做的时候,可能都不会去想什么贪心算法,一鼓作气,就AC了。

我这里其实是为了给大家展现出来 经常被大家忽略的贪心思路,这么一道简单题,就用了两次贪心!

那么本题的解题步骤为:

第一步:将数组按照绝对值大小从大到小排序,注意要按照绝对值的大小
第二步:从前向后遍历,遇到负数将其变为正数,同时K--
第三步:如果K还大于0,那么反复转变数值最小的元素,将K用完
第四步:求和

public class Leetcode1005 {public static int largestSumAfterKNegations(int[] nums, int k) {sort(nums);for (int i = 0; i < nums.length; i++) {if (k > 0 && nums[i] < 0) {nums[i] *= -1;k--;}}if (k % 2 == 1) nums[nums.length - 1] *= -1;int res = 0;for (int num : nums) {res += num;}return res;}public static void sort(int[] nums) {for (int i = 0; i < nums.length; i++) {for (int j = i + 1; j < nums.length; j++) {if (Math.abs(nums[i]) < Math.abs(nums[j])) {int temp = nums[j];nums[j] = nums[i];nums[i] = temp;}}}}
}

 134. 加油站

解题思路:

可以换一个思路,首先如果总油量减去总消耗大于等于零那么一定可以跑完一圈,说明 各个站点的加油站 剩油量rest[i]相加一定是大于等于零的。

每个加油站的剩余量rest[i]为gas[i] - cost[i]。

i从0开始累加rest[i],和记为curSum,一旦curSum小于零,说明[0, i]区间都不能作为起始位置,因为这个区间选择任何一个位置作为起点,到i这里都会断油,那么起始位置从i+1算起,再从0计算curSum。

public class Leetcode134 {public int canCompleteCircuit(int[] gas, int[] cost) {int curSum = 0;int totalSum = 0;int start = 0;for (int i = 0; i < gas.length; i++) {curSum += (gas[i] - cost[i]);totalSum += (gas[i] - cost[i]);if (curSum < 0) {start = i + 1;curSum = 0;}}if (totalSum < 0) return -1;return start;}
}

 135. 分发糖果

public class Leetcode135 {public static int candy(int[] ratings) {int[] candy = new int[ratings.length];Arrays.fill(candy, 1);for (int i = 1; i < ratings.length; i++) {if (ratings[i] > ratings[i - 1]) {candy[i] = candy[i - 1] + 1;}}System.out.println(Arrays.toString(candy));for (int i = ratings.length - 2; i >= 0; i--) {if (ratings[i] > ratings[i + 1]) {candy[i] = Math.max(candy[i + 1] + 1, candy[i]);}}System.out.println(Arrays.toString(candy));int res = 0;for (int i : candy) {res += i;}return res;}
}

http://www.lryc.cn/news/59021.html

相关文章:

  • 比较系统的学习 pandas (2)
  • 怎么查看电脑主板最大支持多少内存?
  • 数据结构——线段树
  • 【C++进阶】实现C++线程池
  • Redis常用五种数据类型
  • C++ Primer第五版_第十一章习题答案(1~10)
  • GEE:使用LandTrendr进行森林变化检测详解
  • docker项目实施
  • springboot实现邮箱验证码功能
  • Java 进阶(5) Java IO流
  • “终于我从字节离职了...“一个年薪40W的测试工程师的自白...
  • 设计模式之策略模式(C++)
  • 从工厂普工到Python女程序员,聊聊这一路我是如何逆袭的?
  • 全国青少年信息素养大赛2023年python·选做题模拟二卷
  • 分布式事务Seata原理
  • 用ChatGPT怎么赚钱?普通人用这5个方法也能赚到生活费
  • ( “树” 之 DFS) 110. 平衡二叉树 ——【Leetcode每日一题】
  • nvm软件使用-同一个环境下控制多个不同node版本
  • 连续两个南航的研究生面试出了从来没出现过的问题,本科和研究生都是计算机专业的,竟然说static是不可更改的。
  • How to install nacos/nacos-server:v2.1.2-slim with docker
  • Rust社区引发舆论危机,问题到底出在哪儿?
  • C++算法恢复训练之归并排序
  • 使用Process Explorer和Clumsy工具定位软件高CPU占用问题
  • 为何巴菲特和马斯克站在了一起?
  • 企业数字化转型全是坑?这几篇数字化转型成功案例,减少70%损失
  • 13.Java面向对象----嵌套类
  • Redis数据迁移过程,使用jedis客户端发送命令,需要注意string和byte类型的命令,如果使用的转换字符编码不一致,会导致丢数据
  • 第六章 IA-32指令类型
  • 基于BenchmarkSQL的Oracle数据库tpcc性能测试
  • Dapr和Rainbond集成,实现云原生BaaS和模块化微服务开发