数据结构——单调栈

前导:

        队列,栈,前面的链接是对普通的栈,和普通的队列的一个讲解,如果没有对普通的栈和队列不了解的小伙伴可以先看看前面链接中的讲解;

        什么是单调,一个序列呈递增或者递减,并且没有一个位置违反了这个递增递减的性质,那么这个序列就算单调序列;

单调栈

        咱么先讲单调栈,什么是单调栈,知名知其意,栈里面的元素应该是单调的;而单调栈的作用就是去维护它里面的元素成单调性,例如它可以用来找某个元素左右侧最近比他大比他小的元素的位置;下面直接来图片演示他是如何操作的:

       初始状态       开始入栈:

        一直入栈直到索引3时: 

        现在继续入栈,到索引5,如果直接入栈索引5又破坏了单调性,那么又需要出栈元素:

        最后通过,这样的操作之后,最终结果为:

单调栈的作用

       单调栈的主要作用是在处理数据序列中,帮助快速解决一些需要维护单调性的问题,例如:
        1. 寻找下一个更大元素或更小元素:单调栈可以用于查找某个元素右侧或左侧的第一个比它大或小的元素,这在解决一些问题中非常有用,比如上图中索引2位置的92右边最近比他小的就是索引3的65;

        2.解决其他需要维护单调性的问题:除了上述示例,单调栈还可用于解决其他需要维护单调性的问题,如找到数组中连续子数组的最大或最小值。

        等等,这些需要思考问题的过程中来进行转换,而不是死记硬背,这个就像数学一样,你背下了公式,但是你也不一定会做题,所以需要多做题进行来加深自己的逻辑框架。

例题:

        这个数据结构直接去实现没有太大的作用,所以选择一个题目进行来讲解:

        leetcode 84

        让你求最大矩形的面积,而这个问题就是进行枚举,然后求每一个矩形的面积,而求每一个矩形的面积如何求,那么这里就可以用到单调栈;

        如何求该位置的面积:

        

        初始化,单调栈:

        然后可能会有疑问,觉得现在还是没有头绪,没关系往后看:

        然后继续上面的操作:

        而从数组右边开始,就是这样:

        同样的维护单调栈的性质,和左边遍历数组的操作一样,我就不画图了;

        然后一直进行这样维护单调栈的性质,最终得到结果:

        然后通过两个数组得到,每个位置可以得到的最大的矩形面积,然后再枚举一次数组,进行得到最终最大矩形面积:

        

        

        最终找到题目要求的答案;

int largestRectangleArea(int* heights, int heightsSize){int n = heightsSize;int l[n + 5], r[n + 5];//创建l,r数组int s[n + 5];//创建栈memset(s, 0, sizeof(s));//初始化清空栈int top = -1;//top = 0,-1都可以,只是有些条件需要变化一下,这是不影响的s[++top] = -1;//入栈虚拟位置for (int i = 0; i < n; i++) {while (top > 0 && heights[s[top]] >= heights[i]) top--;//top > 0,虚拟位置一直存在栈中,就不用再创建新数组来添加虚拟位置,相当于虚拟位置的高度-1在心中l[i] = s[top]; //将最近做左边比i位置高度矮的最近位置记录下来s[++top] = i; //入栈i,现在的栈已经维护到入栈i位置一样成单调递增}top = -1;//初始化栈顶指针s[++top] = n;//将虚拟位置入栈for (int i = n - 1; i >= 0; i--) {//和上面的逻辑一样,就不解释了while (top > 0  && heights[s[top]] >= heights[i]) top--;r[i] = s[top];s[++top] = i;}int ans = 0;for (int i = 0; i < n; i++) {int sum = heights[i] * (r[i] - l[i] - 1);//枚举找每个位置的最大面积ans = fmax(sum, ans);//记录最大矩形面积}return ans;
}

 单调队列明天会出文章续上,这篇已经花了4个小时了,觉得有用给作者一个赞吧;

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Spring-Kafka生产者源码分析

文章目录 概要初始化消息发送小结 概要 本文主要概括Spring Kafka生产者发送消息的主流程 代码准备&#xff1a; SpringBoot项目中maven填加以下依赖 <parent><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-parent&…

Flink提交jar出现错误RestHandlerException: No jobs included in application.

今天打包一个flink的maven工程为jar&#xff0c;通过flink webUI提交&#xff0c;发现居然报错。 如上图所示&#xff0c;提示错误为&#xff1a; Server Response Message: org.apache.flink.runtime.rest.handler.RestHandlerException: No jobs included in application. …

Java 线程池概念总结(thread pool)

一、池化思想的应用 池化思想是一种常见软件设计和优化技术。以下是几个常见池化思想应用场景&#xff1a; 线程池&#xff1a;线程池是池化思想一个典型应用。通过预先创建一组线程并将它们置于就绪状态&#xff0c;以复用线程减少线程创建和销毁的开销&#xff0c;并提高系统…

Auto-GPT 学习笔记

Auto-GPT 学习笔记 Auto-GPT 简介 Auto-GPT 是一个基于 GPT-4 的自主智能体实验项目。它展示了大规模语言模型的规划、记忆和工具使用能力。Auto-GPT 的目标是实现一个完全自主的 AI 代理。GitHub 仓库 Auto-GPT 核心模块 规划(Planning) 使用强化学习策略进行多跳思考。通…

两种动态代理比较(补充),进程通信方式总结

jdk和CGLib动态代理: jdk动态代理&#xff1a; java提供的动态代理技术&#xff1b; spring aop默认采用的方式&#xff1b; 只能对实现了至少一个接口的类生成代理对象&#xff1b; CGLib动态代理&#xff1a; 采用底层字节码技术&#xff1b; 目标对象没有实现接口时采…

Nginx特性应用及载装

Nginx是一款轻量级的Web 服务器/反向代理服务器及电子邮件(IMAP/POP3)代理服务器。其特点是占有内存少&#xff0c;并发能力强&#xff0c;事实上nginx的并发能力在同类型的网页服务器中表现较好&#xff0c;中国大陆使用nginx的网站有&#xff1a;网易、腾讯、阿里等。 …

文字识别的

对于 PDF 提取文字&#xff0c;Tesseract OCR 是一个常用的工具。你可以使用 Tesseract OCR 的 Java API 来实现。以下是一个使用 Tesseract OCR 提取 PDF 文档文字的简单示例代码&#xff1a; import net.sourceforge.tess4j.Tesseract; import net.sourceforge.tess4j.Tesse…

MyBatis-Plus —— 初窥门径

前言 在前面的文章中荔枝梳理了MyBatis及相关的操作&#xff0c;作为MyBatis的增强工具&#xff0c;MyBatis-Plus无需再在xml中写sql语句&#xff0c;在这篇文章中荔枝将梳理MyBatis-Plus的基础知识并基于SpringBoot梳理MyBatis-Plus给出的两个接口&#xff1a;BaseMapper和ISe…

对象模型和this指针(个人学习笔记黑马学习)

1、成员变量和成员函数 #include <iostream> using namespace std; #include <string>//成员变量和成员函数分开存储class Person {int m_A;//非静态成员变量 属于类的对象上的static int m_B;//静态成员变量 不属于类的对象上void func() {} //非静态成员函数 不…

LeetCode 1921. Eliminate Maximum Number of Monsters【贪心,计数排序】1527

本文属于「征服LeetCode」系列文章之一&#xff0c;这一系列正式开始于2021/08/12。由于LeetCode上部分题目有锁&#xff0c;本系列将至少持续到刷完所有无锁题之日为止&#xff1b;由于LeetCode还在不断地创建新题&#xff0c;本系列的终止日期可能是永远。在这一系列刷题文章…

供应链 | 顶会CIKM论文精读:面向大规模三维装箱问题的数据驱动树形搜索算法

论文解读&#xff1a;丁建辉&#xff0c;李明哲&#xff0c;赵艳蓉&#xff0c;孙楚天 编者按 本次解读的文章发表于CCF-B类会议30th ACM International Conference on Information and Knowledge Management。摘要总结如下&#xff1a; 3维装箱问题&#xff08;3D-BPP&#…

Redis的缓存穿透,缓存击穿,缓存雪崩

1. 缓存穿透 什么是缓存穿透&#xff1f; 缓存穿透说简单点就是大量请求的 key 是不合理的&#xff0c;根本不存在于缓存中&#xff0c;也不存在于数据库中 。这就导致这些请求直接到了数据库上&#xff0c;根本没有经过缓存这一层&#xff0c;对数据库造成了巨大的压力&…

雪花算法生成id分析与实践

目录 1 什么是雪花算法&#xff1f; 结构 优点 缺点 2 在java中使用 使用注意&#xff1a; 测试代码 效果 1 什么是雪花算法&#xff1f; witter的雪花算法&#xff08;Snowflake Algorithm&#xff09;。雪花ID是一种分布式唯一ID生成算法&#xff0c;旨在解决分布式…

业绩走低,毛利率下滑,海外市场能否成为极米科技救命稻草?

撰稿|行星 来源|贝多财经 8月30日&#xff0c;成都极米科技股份有限公司&#xff08;SH:688696&#xff0c;下称“极米科技”&#xff09;发布2023年半年度业绩报告。财报显示&#xff0c;极米科技2023年上半年的业绩出现了大幅下滑&#xff0c;其中收入同比减少两成&#xf…

代码随想录二刷day06

提示&#xff1a;文章写完后&#xff0c;目录可以自动生成&#xff0c;如何生成可参考右边的帮助文档 文章目录 前言一、力扣242. 有效的字母异位词二、力扣349. 两个数组的交集三、力扣202. 快乐数四、力扣1两数之和 前言 一、力扣242. 有效的字母异位词 class Solution {pub…

数学建模-点评笔记 9月3日

1.摘要&#xff1a;关键方法和结论&#xff08;精炼的语言&#xff09;要说明&#xff0c;方法的合理性和意义也可以说明。 评委先通过摘要筛选&#xff08;第一轮&#xff09; 2.时间序列找异常值除了3西格玛还有针对时间序列更合适寻找的方法 3.模型的优缺点要写的详细一点…

世微AP9234 升压型DC/DC LED恒流驱动

描述 AP9234是一款由基准电压源、振荡电路、误差放大电路、相位补偿电路、电流限制电路等构成的CMOS升压型DC/DC LED驱动。由于内置了低导通电阻的增强型N沟道功率MOSFET&#xff0c;因此适用于需要高效率、高输出电流的应用电路。另外&#xff0c;可通过在VSENSE端子连接电流…

754. 到达终点数字

754. 到达终点数字 原题链接&#xff1a;完成情况&#xff1a;解题思路&#xff1a;参考代码&#xff1a; 原题链接&#xff1a; 754. 到达终点数字 https://leetcode.cn/problems/reach-a-number/description/ 完成情况&#xff1a; 解题思路&#xff1a; 牛顿莱布尼茨梯…

softmax的cuda编程详细解读——算子融合

softmax介绍 在上一篇博客我们介绍了softmax的内容以及相关的编程实现,总结一下softmax的特点如下:(没有特殊说明的情况下,考虑的仍然只是1D向量 x x x) 1:获得向量的全局最大值M 2:针对向量 x ^ = { exp ⁡ ( x i −

vue3 组件通信方式

文章目录 组件通信方式props自定义事件全局事件总线v-modeluseAttrsref与$parentprovide与injectpiniaslot 组件通信方式 props ​ 实现父子组件通信,在vue3中可以通过defineProps获取父组件传递的数据。且在组件内部不需要引入defineProps方法可以直接使用&#xff01; 父组…