代码随想录第32天|455.分发饼干 376. 摆动序列

理论基础

贪心算法核心:选择每一阶段的局部最优,从而达到全局最优。

455.分发饼干

455. 分发饼干 - 力扣(LeetCode)代码随想录 (programmercarl.com)455. 分发饼干 - 力扣(LeetCode)

贪心算法理论基础!_哔哩哔哩_bilibili 

假设你是一位很棒的家长,想要给你的孩子们一些小饼干。但是,每个孩子最多只能给一块饼干。

对每个孩子 i,都有一个胃口值 g[i],这是能让孩子们满足胃口的饼干的最小尺寸;并且每块饼干 j,都有一个尺寸 s[j] 。如果 s[j] >= g[i],我们可以将这个饼干 j 分配给孩子 i ,这个孩子会得到满足。你的目标是尽可能满足越多数量的孩子,并输出这个最大数值。

示例 1:

输入: g = [1,2,3], s = [1,1]
输出: 1
解释: 
你有三个孩子和两块小饼干,3个孩子的胃口值分别是:1,2,3。
虽然你有两块小饼干,由于他们的尺寸都是1,你只能让胃口值是1的孩子满足。
所以你应该输出1。

示例 2:

输入: g = [1,2], s = [1,2,3]
输出: 2
解释: 
你有两个孩子和三块小饼干,2个孩子的胃口值分别是1,2。
你拥有的饼干数量和尺寸都足以让所有孩子满足。
所以你应该输出2.

提示:

  • 1 <= g.length <= 3 * 104
  • 0 <= s.length <= 3 * 104
  • 1 <= g[i], s[j] <= 231 - 1

局部最优就是把大的饼干尽量喂给大胃口的小孩,这样才不会浪费。

先将饼干和小孩分别排序:

Arrays.sort(s);
Arrays.sort(g);

从大饼干对应大胃口小孩开始匹配:

for(int index = g.length - 1; index >= 0; index--){
    if(start >= 0 && g[index] <= s[start]){
        start--;
        count++;
    }
}

综合代码:

class Solution {
    // 思路2:优先考虑胃口,先喂饱大胃口
    public int findContentChildren(int[] g, int[] s) {
        Arrays.sort(g);
        Arrays.sort(s);
        int count = 0;
        int start = s.length - 1;
        // 遍历胃口
        for (int index = g.length - 1; index >= 0; index--) {
            if(start >= 0 && g[index] <= s[start]) {
                start--;
                count++;
            }
        }
        return count;
    }
}

376. 摆动序列

376. 摆动序列 - 力扣(LeetCode)

代码随想录 (programmercarl.com)

贪心算法,寻找摆动有细节!| LeetCode:376.摆动序列_哔哩哔哩_bilibili

如果连续数字之间的差严格地在正数和负数之间交替,则数字序列称为 摆动序列 。第一个差(如果存在的话)可能是正数或负数。仅有一个元素或者含两个不等元素的序列也视作摆动序列。

  • 例如, [1, 7, 4, 9, 2, 5] 是一个 摆动序列 ,因为差值 (6, -3, 5, -7, 3) 是正负交替出现的。

  • 相反,[1, 4, 7, 2, 5] 和 [1, 7, 4, 5, 5] 不是摆动序列,第一个序列是因为它的前两个差值都是正数,第二个序列是因为它的最后一个差值为零。

子序列 可以通过从原始序列中删除一些(也可以不删除)元素来获得,剩下的元素保持其原始顺序。

给你一个整数数组 nums ,返回 nums 中作为 摆动序列 的 最长子序列的长度 。

示例 1:

输入:nums = [1,7,4,9,2,5]
输出:6
解释:整个序列均为摆动序列,各元素之间的差值为 (6, -3, 5, -7, 3) 。

示例 2:

输入:nums = [1,17,5,10,13,15,10,5,16,8]
输出:7
解释:这个序列包含几个长度为 7 摆动序列。
其中一个是 [1, 17, 10, 13, 10, 16, 8] ,各元素之间的差值为 (16, -7, 3, -3, 6, -8) 。

示例 3:

输入:nums = [1,2,3,4,5,6,7,8,9]
输出:2

提示:

  • 1 <= nums.length <= 1000
  • 0 <= nums[i] <= 1000

进阶:你能否用 O(n) 时间复杂度完成此题?

局部最优:删掉单调坡上的节点,这个坡度就可以有两个局部峰值。

整体最优:整个序列有最多的局部峰值,从而达到最长的摆动序列。

按照以上的图可以分析出来,不需要删除元素,重点在于统计数组的峰值数量

那什么时候需要统计波动呢?有两种情况

1、prediff(nums[i] - nums[i-1])<0 且 curdiff(nums[i+1] - nums[i])>0

2、prediff(nums[i] - nums[i-1])>0 且 curdiff(nums[i+1] - nums[i])<0

以上情况只适用于i位于非首尾位置的时候。如果i位于首尾,则prediff和curdiff都无法计算,那i位于首尾的时候是什么情况呢?还有平坡的时候是prediff或者curdiff等于0,这时候应该怎么计算呢?

情况一上下坡中有平坡

实际摆长为3,要么删除前面3个2,要么删除后面3个2:
 

 删左面三个 2 的规则,那么 当 prediff = 0 && curdiff < 0 也要记录一个峰值,因为他是把之前相同的元素都删掉留下的峰值。

情况二、i位于数组首尾两端:

当i位于首端的时候,假设数组最前面的数字和i所在的首端的位置相同:
 

 

针对以上情形,result 初始为 1(默认最右面有一个峰值),此时 curDiff > 0 && preDiff <= 0,那么 result++(计算了左面的峰值),最后得到的 result 就是 2(峰值个数为 2 即摆动序列长度为 2)

代码如下:

class Solution {
    public int wiggleMaxLength(int[] nums) {
        // 如果数组长度小于等于1,直接返回数组长度
        if (nums.length <= 1) {
            return nums.length;
        }
        // 当前差值
        int curDiff = 0;
        // 上一个差值
        int preDiff = 0;
        // 计数,初始为1,因为序列中至少有一个元素
        int count = 1;
        // 遍历数组
        for (int i = 1; i < nums.length; i++) {
            // 计算当前差值
            curDiff = nums[i] - nums[i - 1];
            // 如果当前差值和上一个差值为一正一负,或者等于0(初始时的preDiff)
            if ((curDiff > 0 && preDiff <= 0) || (curDiff < 0 && preDiff >= 0)) {
                // 计数加1
                count++;
                // 更新上一个差值
                preDiff = curDiff;
            }
        }
        // 返回计数,即摆动子序列的长度
        return count;
    }
}

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

LeetCode:1483. 树节点的第 K 个祖先(倍增 Java)

目录 1483. 树节点的第 K 个祖先 题目描述&#xff1a; 实现代码与解析&#xff1a; 倍增 原理思路&#xff1a; 1483. 树节点的第 K 个祖先 题目描述&#xff1a; 给你一棵树&#xff0c;树上有 n 个节点&#xff0c;按从 0 到 n-1 编号。树以父节点数组的形式给出&#…

【Vue】Vue3中的OptionsAPI与CompositionAPI

文章目录 OptionsAPICompositionAPI对比总结 OptionsAPI 中文名:选项式API通过定义methods,computed,watch,data等属性方法&#xff0c;处理页面逻辑。以下是OptionsAPI代码结构 实例代码: <script lang"ts">// js或者tsimport { defineComponent } from vu…

HubSpot如何通过自动化和优化客户服务流程,提升客户满意度和忠诚度?

HubSpot通过自动化和优化客户服务流程&#xff0c;可以有效地提升客户满意度和忠诚度。以下是HubSpot实现这一目标的几个关键步骤&#xff1a; 建立清晰的服务流程&#xff1a;首先&#xff0c;HubSpot帮助企业建立清晰、标准化的客户服务流程。这包括明确的服务阶段定义&…

git分支 - 分支简介

分支 几乎每个版本控制系统都有某种形式的分支支持。分支意味着偏离了主开发线&#xff0c;并继续进行工作&#xff0c;而不会影响到主开发线。在许多版本控制系统工具中&#xff0c;这是一个比较昂贵的过程&#xff0c;通常需要创建源代码目录的一个新副本&#xff0c;对于大…

第7章 数据安全

思维导图 7.1 引言 数据安全包括安全策略和过程的规划、建立与执行&#xff0c;为数据和信息资产提供正确的身份验证、授权、访问和审计。虽然数据安全的详细情况(如哪些数据需要保护)因行业和国家有所不同&#xff0c;但是数据安全实践的目标是相同的&#xff0c;即根据隐私和…

链表之双向链表的实现

铁汁们大家好&#xff0c;我们上一篇博客学习了单链表&#xff0c;这节课让我们继续往深学习&#xff0c;学习一下双线链表&#xff0c;话不多说&#xff0c;我们开始吧&#xff01; 目录 1.双向链表 2.顺序表和链表的优缺点 3.双向链表的实现 1.双向链表 1.我们要实现的双线…

Elasticsearch快速上手

基本概念 索引&#xff08;Index&#xff09; 索引是文档的容器&#xff0c;就像关系数据库中&#xff0c;要存储行记录必须先创建数据库和表一样。 类型&#xff08;Type&#xff09; ES6 及之前的版本还存在”类型“的概念&#xff0c;一个索引下可以存储多个类型的文档&am…

探索数据结构:特殊的双向队列

✨✨ 欢迎大家来到贝蒂大讲堂✨✨ &#x1f388;&#x1f388;养成好习惯&#xff0c;先赞后看哦~&#x1f388;&#x1f388; 所属专栏&#xff1a;数据结构与算法 贝蒂的主页&#xff1a;Betty’s blog 1. 双向队列的定义 **双向队列(double‑ended queue)**是一种特殊的队列…

Ant Design Pro | 前端项目初始化

初始化项目 环境确认 这里使用的版本如下&#xff1a; 新建文件夹&#xff08;fapi&#xff09; 执行项目初始化命令 cmd进入命令行执行项目初始化命令&#xff0c;参考官网https://pro.ant.design/zh-CN/ # 使用 npm npm i ant-design/pro-cli -g # fapi-frontend是项目…

树莓派固件烧录教程(2024)

一、烧录工具准备 硬件准备&#xff1a; 16G及以上TF卡和读卡器&#xff0c;TF卡建议高速卡&#xff08;卡的读写速度直接影响树莓派的运行速度&#xff09;。 软件准备&#xff1a;&#xff08;下面二方法选其一即可&#xff09; 方法1&#xff1a;raspberry官方烧录工具R…

【高校科研前沿】中国科学院南京地理与湖泊研究所肖启涛博士为一作在Sci. Bull发文:我国湖泊二氧化碳从大气的源向汇转变

目录 1.文章简介 2.研究内容 3.文章引用 1.文章简介 论文名称&#xff1a;Lakes shifted from a carbon dioxide source to a sink over past two decades in China 第一作者及通讯作者&#xff1a;肖启涛&#xff08;博士生&#xff09;&#xff0c;段洪涛&#xff08;研究…

JavaSE继承和多态(下)

在了解多态之前我们先弄清以下三个概念&#xff1a; 方法的重写向上转型和向下转型动态绑定和静态绑定 一.方法的重写 重写(override)&#xff1a;也称为覆盖。重写是子类对父类非静态、非private修饰&#xff0c;非final修饰&#xff0c;非构造方法等的实现过程 进行重新编写,…

如何使用 langchain 与 openAI 连接

上一篇写了如何安装 langchain https://www.cnblogs.com/hailexuexi/p/18087602 这里主要说一个 langchain的使用 创建一个目录 langchain &#xff0c;在这个目录下创建两个文件 main.py 这段python代码&#xff0c;用到了openAI&#xff0c;需要openAI及FQ。这里只做…

c++的学习之路:16、string(3)

上章有一些东西当时没学到&#xff0c;这里学到了将在补充&#xff0c;文章末附上代码&#xff0c;思维导图。 目录 一、赋值重载 二、带模板的创建 三、析构函数 四、代码 五、思维导图 一、赋值重载 这里的赋值重载就是直接利用交换函数进行把传参生成的临时数据和需要…

IDEA中的Debug功能介绍

说明&#xff1a;本文介绍IDEA中的Debug功能&#xff0c;基于2023.2&#xff08;Ultimate Edition&#xff09;版本 简单介绍 首先&#xff0c;在程序需要停止的所在行号上&#xff0c;鼠标左键&#xff0c;可设置一个断点&#xff0c;是一个红色圆点标志&#xff0c;表示程序…

2023年下半年中级软件设计师上午真题及答案解析

01 02 03 04 05 06 07 08 09 10 篇幅有限&#xff0c;私我获取免费完整 pdf文件

php反序列化题目

[NewStarCTF 公开赛赛道]UnserializeOne 分析代码&#xff0c;最终需要调用到 file_get_contents 即可获得flag 从后往前分析 触发 __invoke 需要 以调用函数的方式调用一个对象 可以找到Start类 里的__isset中可以将类当作函数调用 所以需要调用到 __isset 就需要 isset()…

Steam上线真人乙游,女性玩家还愿意买单吗?

Steam上线了一款真人乙游《糟糕&#xff01;他们太爱我了怎么办&#xff1f;》&#xff08;以下简称《糟糕&#xff01;&#xff09;。 乍一听这个游戏名&#xff0c;似乎和《完蛋&#xff01;我被美女包围了&#xff01;》有异曲同工之妙&#xff0c;事实也确实如此&#xff…

实现通讯录(顺序表版本)

一、功能要求 &#xff08;1&#xff09;⾄少能够存储100个⼈的通讯信息 &#xff08;2&#xff09;能够保存⽤⼾信息&#xff1a;名字、性别、年龄、电话、地址等 &#xff08;3&#xff09;增加联系⼈信息 &#xff08;4&#xff09;删除指定联系⼈ &#xff08;5&#…

国内:深圳交通流量数据集

数据来源&#xff1a;深圳政府数据开放平台&#xff08;深圳市政府数据开放平台&#xff09;&#xff0c;这个官网上还有其他类数据集&#xff0c;值得收藏&#xff01;&#xff01;&#xff01; 数据集介绍&#xff1a;宝安区-G4高速西乡大道入口车流量统计 第一行每列的标题…