LeetCode算法(双指针)

今天的题目主要都是力扣前100中,关于双指针的题

1.移动零

链接:移动零

示例:

示例 :

输入: nums =[0,1,0,3,12]

输出:[1,3,12,0,0]

可以看到保持原有元素的顺序,将所有的0,移动到数组最后方即可。

这道题看见思路很明确,就是遍历数组,碰到0了,进行位置互换。这个题目实际上和数组的元素移除几乎是一样的,只不过元素删除是进行覆盖,而移动0是进行元素移动

思路:

(1)定义两个指针,一个为快指针(负责遍历数组),另一个为慢指针(负责标记0)

(2)快指针进行移动遍历,如果发现0元素,则不进行任何操作,如果不是0元素,则进行与慢指针的元素互换

代码如下:

public class MobileZero {/*移动0*///思路:双指针法//快慢指针同时移动,一个指针用于标记0,一个指针移动,非0则交换两个指针,0则继续移动public void moveZeroes(int[] nums) {//慢指针:标记非0元素的位置int slowCur = 0;//快指针:遍历数组for (int cur = 0; cur < nums.length; cur++) {if (nums[cur] != 0){int temp = nums[cur];nums[cur] = nums[slowCur];nums[slowCur] = temp;//移动慢指针slowCur++;}}}}

2.三数之和

链接:三数之和

示例:

给你一个包含 n 个整数的数组 nums,判断 nums 中是否存在三个元素 a,b,c ,使得 a + b + c = 0 ?请你找出所有满足条件且不重复的三元组。

给定数组 nums = [-1, 0, 1, 2, -1, -4],

满足要求的三元组集合为: [ [-1, 0, 1], [-1, -1, 2] ]

这道题我的大概思路就是,遍历所有元素,并找到每个元素对应的两个符合条件的数字,那既然需要两个数字,就需要使用双指针了

那么下一个问题就是,指针该指向哪里,并如何移动呢?

首先就需要将数组进行排序,因为有了顺序性,才有移动的规律,当我们将数组排序后

[-4,-1,-1,0,1,2] 

遍历整个数组的所有元素,并把其当作a
三种情况:
1.a+b+c=0 这种情况符合要求,添加到列表中
2.a+b+c>0 这种情况说明,a+b<c 所以c要减小
3.a+b+c<0 这种情况说明,a+b>c 所以b要增大

换成指针来说,减小和增大就要移动,那么位置我设置的头指针指向a+1,尾指针指向数组末尾

第二种情况:尾指针向前移动

第三种情况:头指针向后移动

代码如下:

import java.util.*;public class SumOfThreeNumbers {/*三数之和*/public List<List<Integer>> threeSum(int[] nums) {//思路:a + b + c = 0//采用双指针思路,遍历所有元素,并把其当作a,然后寻找 b + c = -a 的元素//头指针指向a+1,尾指针指向数组末尾,数组排序//遍历整个数组的所有元素,寻找每个元素的对应数值//三种情况://1.a+b+c=0 这种情况符合要求,添加到列表中//2.a+b+c>0 这种情况说明,a+b<c 所以c要减小,尾指针向前移动//3.a+b+c<0 这种情况说明,a+b>c 所以b要增大,头指针向后移动//去重处理:在进入遍历数组时,判断当前元素是否等于上一个元素,如果相等则跳过该元素的遍历//对指针进行处理:因为指针的遍历也会重复,所以采用while循环// 如果移动的下一个元素相等,那么指向下一个元素,然后进行自增List<List<Integer>> result = new ArrayList<>();Arrays.sort(nums);for (int i = 0; i < nums.length; i++) {//去重操作,防止遍历的元素重复if (i > 0 && nums[i] == nums[i - 1]){continue;}//在每次循环中,来移动头指针和尾指针int left = i + 1;int right = nums.length - 1;//移动指针并寻找满足条件的元素while(left < right){int num = nums[i] + nums[left] + nums[right];//满足条件if (num == 0){List<Integer> list = new ArrayList<>();list.add(nums[i]);list.add(nums[left]);list.add(nums[right]);result.add(list);//去重处理:防止指针所指向的元素重复while(left < right && nums[left] == nums[left + 1]){left++;}while(left < right && nums[right] == nums[right - 1]){right--;}//移动指针,寻找当前元素的其他对应元素left++;right--;} else if (num > 0) {//c过大,尾指针左移right--;}else {//b过小,头指针右移left++;}}}return result;}}

3.盛最多水的容器

链接:盛最多水的容器

给定一个长度为 n 的整数数组 height 。有 n 条垂线,第 i 条线的两个端点是 (i, 0) 和 (i, height[i]) 。

找出其中的两条线,使得它们与 x 轴共同构成的容器可以容纳最多的水。

返回容器可以储存的最大水量。

示例 :

输入:[1,8,6,2,5,4,8,3,7]
输出:49
解释:图中垂直线代表输入数组 [1,8,6,2,5,4,8,3,7]。在此情况下,容器能够容纳水(表示为蓝色部分)的最大值为 49。

思路:

简单理解,就是寻找最大乘积,底 x 高的最大值,其实这里可以直接使用循环不去思考,双指针移动,遍历每一根柱子与其他柱子形成的底,和取两个柱子最短的进行相乘,找到最大值就好了,但是会超时,所以,又要考虑双指针的移动问题(选高柱子会漏水)

首先将问题拆分,最大值无非就是找到,底最大,高最大的值,如果我们先从高入手,那么就是将数组进行排序,可是这样,毫无规律,又要进行遍历,所以试试从底入手

那么最大底,一定是第一个柱子和最后一个柱子形成的底最大,然后比较两者谁更矮,移动指向矮的那一边的指针

因为下一个指向,如果还比最后一个柱子矮,则会继续向尾部移动寻找,如果高,尾部向头部移动。

代码如下:

import java.util.HashMap;public class TheContainerWithTheMostWaterCapacity {/*盛水最多的容器*/public int maxArea(int[] height) {//思路:定义两个指针,一个指向第一个值,一个指向最后一个值//根据索引计算底宽,根据值的大小判断高,小的做高//哪边的值小,则对应的指针移动,更新最大值int beforeCur = 0;int behindCur = height.length - 1;int maxVolume = 0;while (beforeCur < behindCur) {int bottom = behindCur - beforeCur;int high = Math.min(height[beforeCur], height[behindCur]);maxVolume = Math.max(maxVolume, bottom * high);if (height[beforeCur] > height[behindCur]) {behindCur--;} else {beforeCur++;}}return maxVolume;}}

 今天的题更多的是思路吧,比起前面的基础数据结构知识,会更复杂,更考验读题,今天的练习就到这里!谢谢大家

 

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

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

相关文章

开源项目工具:LeanTween - 为Unity 3D打造的高效缓动引擎详解(比较麻烦的API版)

1.LeanTween.reset() 一、工具介绍 参考&#xff1a;推荐开源项目&#xff1a;LeanTween - 为Unity 3D打造的高效缓动引擎-CSDN博客 LeanTween是一个专为Unity 3D引擎设计的高效缓动&#xff08;tweening&#xff09;库&#xff0c;它提供了简单易用的API&#xff0c;帮助开…

ctfshow(175->178)--SQL注入--联合注入及其过滤

Web175 进入界面&#xff1a; 审计&#xff1a; 查询语句&#xff1a; $sql "select username,password from ctfshow_user5 where username !flag and id ".$_GET[id]." limit 1;";返回逻辑&#xff1a; if(!preg_match(/[\x00-\x7f]/i, json_enc…

数据结构(8.4_3)——堆的插入删除

在堆中插入新元素 在堆中删除元素 总结&#xff1a;

Linux:权限的深度解析(小白必看!!!)

文章目录 前言一、Linux重要的几个热键二、关机三、扩展命令总结四、shell命令以及运行原理感性理解五、Linux权限的概念1. 权限的概念2. 认识人&#xff08;用户&#xff09;1&#xff09;创建人2&#xff09;人分类3&#xff09;人切换4&#xff09;指令提权 3. ll下文件的权…

一些待机电流波形特征

一、待机电流波形 最干净的待机电流波形应该只有paging&#xff0c;不过需要注意2点&#xff1a; 每个paging的间隔&#xff0c;不同网络可能不一样&#xff0c;有可能是320ms, 640ms 待机网络 paging 间隔 1分钟的耗电量 单个耗电量 单个待机电流 单个波形时长 4G 64…

二十三、Python基础语法(包)

包(package)&#xff1a;包是一种组织代码的方式&#xff0c;可以将相关的模块组合在一起&#xff0c;以便更好地管理和重用代码&#xff0c;包的目录中有一个特殊代码文件__init__.py&#xff0c;包的命名也要遵循标识符的规则。 一、包的结构 一个 Python 包通常是一个包含…

NLTK无法下载?

以下内容仅为当前认识&#xff0c;可能有不足之处&#xff0c;欢迎讨论&#xff01; 文章目录 nltk无法下载怎么办&#xff1f;什么是NLTK&#xff1f;为什么要用NLTK&#xff1f;如何下载&#xff1f; nltk无法下载怎么办&#xff1f; 什么是NLTK&#xff1f; NLTK是学习自然…

python项目实战——多协程下载美女图片

协程 文章目录 协程协程的优劣势什么是IO密集型任务特点示例与 CPU 密集型任务的对比处理 I/O 密集型任务的方式总结 创建并使用协程asyncio模块 创建协程函数运行协程函数asyncio.run(main())aiohttp模块调用aiohttp模块步骤 aiofiles————协程异步函数遇到的问题一 await …

代码随想录跟练21天——LeetCode332.重新安排行程, 51. N皇后,37. 解数独

332.重新安排行程 力扣题目链接(opens new window) 给定一个机票的字符串二维数组 [from, to]&#xff0c;子数组中的两个成员分别表示飞机出发和降落的机场地点&#xff0c;对该行程进行重新规划排序。所有这些机票都属于一个从 JFK&#xff08;肯尼迪国际机场&#xff09;出…

【Python可视化系列】一文教你绘制双Y轴的双折线图(案例+源码)

这是我的第369篇原创文章。 一、引言 在日常工作和学习中&#xff0c;我们会遇到将两个折线画在一张图上的情况&#xff0c;且这两个折线代表了两个特征&#xff0c;具有不同的涵义和量纲表示&#xff0c;这时候我们就需要绘制一个双Y轴折线图&#xff0c;一边代表一个特征&…

Redis 持久化 总结

前言 相关系列 《Redis & 目录》&#xff08;持续更新&#xff09;《Redis & 持久化 & 源码》&#xff08;学习过程/多有漏误/仅作参考/不再更新&#xff09;《Redis & 持久化 & 总结》&#xff08;学习总结/最新最准/持续更新&#xff09;《Redis & …

python进阶集锦

一、迭代器和生成器 区别 关于迭代器和生成器 迭代器与生成器的区别 迭代器&#xff08;Iterator&#xff09;和生成器&#xff08;Generator&#xff09;是Python中处理序列数据的两种不同概念。迭代器是遵循迭代协议的对象&#xff0c;而生成器是一种特殊类型的迭代器&am…

Vue学习笔记(八)

透传attribute "透传attribute"指的是传递给一个组件&#xff0c;却没有被改组件声明为props或emits的attribute或者v-on事件监听器。最常见的例子就是class、style和id。 当一个组件以单个元素为根作渲染时&#xff0c;透传的attribute会自动被添加到根元素上。 …

4个提取音频办法,轻松实现视频转音频!

在信息爆炸的时代&#xff0c;视频内容以其直观、生动的特点占据了互联网的大半江山。然而&#xff0c;在某些场景下&#xff0c;我们可能更倾向于只听取音频部分&#xff0c;无论是驾驶途中听讲座、跑步时享受音乐视频中的纯音乐的场景&#xff0c;还是为了节省流量和存储空间…

C++ 类与对象入门:基础知识与定义

引言&#xff1a; 本来打算用一篇介绍清楚C中的类与对象&#xff0c;再三考虑后觉得不妥&#xff1a;第一&#xff0c;知识点实在太多&#xff1b;第二&#xff0c;对于从刚学完C并打算过渡到C的朋友来说&#xff0c;学的太深较有难度… 总而言之&#xff0c;我打算用三到四篇文…

一篇文章总结 SQL 基础知识点

1. 官方文档 MySQL&#xff1a;https://dev.mysql.com/doc/refman/8.4/en/ SQL Server&#xff1a;What is SQL Server? - SQL Server | Microsoft Learn Oracle&#xff1a;https://docs.oracle.com/en/database/oracle/oracle-database/23/lnpls/loe.html 2. 术语 SQL S…

电脑程序变化监控怎么设置?实时监控电脑程序变化的五大方法,手把手教会你!

​在现代办公和信息安全领域&#xff0c;实时监控电脑程序变化是一项至关重要的任务。 无论是企业内网安全、员工行为审计&#xff0c;还是个人电脑的隐私保护&#xff0c;了解并设置有效的监控方法都是必不可少的。 本文将详细介绍五种电脑程序变化监控的方法&#xff0c;帮助…

️ Vulnhuntr:利用大型语言模型(LLM)进行零样本漏洞发现的工具

在网络安全领域&#xff0c;漏洞的发现和修复是保护系统安全的关键。今天&#xff0c;我要向大家介绍一款创新的工具——Vulnhuntr&#xff0c;这是一款利用大型语言模型&#xff08;LLM&#xff09;进行零样本漏洞发现的工具&#xff0c;能够自动分析代码&#xff0c;检测远程…

SAP-ABAP开发学习-FUNCTION ALV

ALV概览 ALV全称SAP List View&#xff0c;是SAP提供的一个强大的数据报表显示工具。ALV实质上是一个屏幕控件对象&#xff0c;它通过程序传递数据内表的方式来显示数据。 实现方式&#xff1a;调用标准函数&#xff1b;优化接口:用户可以实现对字段的排序、筛选及统计等功能。…

51c嵌入式~IO合集1

我自己的原文哦~ https://blog.51cto.com/whaosoft/12383193 一、单片机通信数据接收解析方法 前阵子一朋友使用单片机与某外设进行通信时&#xff0c;外设返回的是一堆格式如下的数据&#xff1a; AA AA 04 80 02 00 02 7B AA AA 04 80 02 00 08 75 AA AA 04 80 02 00 9B E2…