双指针问题2

news2024/12/23 6:56:13

文章目录

  • 1. 有效三角形的个数(611)
  • 2. 查找总价格为目标值的两个商品(LCR179)
  • 3. 三数之和(15)
  • 4. 四数之和(18)


1. 有效三角形的个数(611)

题目描述:
在这里插入图片描述

算法原理:
这题使用的方法要进行理解首先要知道一个比较基础的数学知识就是三角形的三条边当中只要最短的那两条边的和大于第三条边那么这三条边就是可以构成三角形的,具体原因就不阐述了其实也很简单。
知道了这个数学知识我们首先要做的就是将数组进行升序排序,以此来方便我们后续进行操作。我们从数组的最后一个元素开始遍历到数组的2下标的元素,这个元素位置记为i,事实上可以使用for循环完成这个遍历。然后对于i位置元素的左边的数组元素进行分析,在for循环内部定义left指针指向0位置,right指针指向i-1位置。因为我们将nums[i]的值视为第三条边的长度,nums[left]和nums[right]视为第一条边和第二条边的长度,那么此时分为两种情况。
第一种情况就是nums[left]+nums[right]>nums[i]那么此时是可以构成三角形的,因为nums[left]加上nums[right]都可以大于nums[i],显然在nums数组的left+1~right-1下标的元素加上nums[right]都会大于nums[i],也就是可以构成三角形,所以我们无需去遍历这个区间内的元素就可以直接得到在固定三角形第二条边和第三条边长度的情况下有多少种不同可以构成三角形的三元组,最终将right–,并且将最终返回的ret也就是返回的可以构成三角形的三元组的个数加上right-left。
第二种情况就是nums[left]+nums[right]<=nums[i]那么此时是不可以构成三角形的,因为此时连nums[right]加上nums[left]都已经小于nums[i],显然在nums数组的left+1~right-1下标的元素加上nums[left]都会小于nums[i],也就是不可以构成三角形,所以也是一样我们无需去遍历这个区间内的元素直接跳过即可,最终将left++。
重复以上两种情况的判断,直至right和left相遇,这相当于在开始的for循环中再去写一个循环去处理nums数组的0~i-1这个区间,具体逻辑如代码所示。
代码如下:

class Solution {
    public int triangleNumber(int[] nums) {
        int n = nums.length;
        Arrays.sort(nums);
        int ret = 0;
        for (int i = n - 1; i >= 2; i--) {
            int left = 0;
            int right = i - 1;
            while (left < right) {
                int temp = nums[left] + nums[right];
                if (temp > nums[i]) {
                    ret += right - left;
                    right--;
                } else {
                    left++;
                }
            }
        }
        return ret;
    }
}

题目链接

2. 查找总价格为目标值的两个商品(LCR179)

题目描述:
在这里插入图片描述

算法原理:
其实这一题是可以使用二分查找直接做出来的,但是在学习一种方法的时候就要尽量多的去使用它,从而逐渐熟练,因此这里使用双指针的方法。跟上题使用相似的思想,就是定义left和right指针来不断缩小区间范围,满足条件跳出循环然后返回一种结果即可。
代码如下:

class Solution {
    public int[] twoSum(int[] price, int target) {
        int right = price.length - 1;
        int left = 0;

        while (left < right) {
            if (price[left] + price[right] > target) {
                right--;
            } else if (price[left] + price[right] < target) {
                left++;
            } else {
                break;
            }
        }

        return new int[] { price[left], price[right] };
    }
}

题目链接

3. 三数之和(15)

题目描述:
在这里插入图片描述

算法原理:
这一题也是和前面的思想类似,不过这里需要先给数组排序得到升序的数组,然后固定住第三个数nums[i](这里的i可以取2到nums.length-1,2是因为至少要留两个值作为前两个数),在0到i-1这个区间内去找到两个值满足nums[left]+nums[right]=-nums[i],这一题就转化为和第一题一致的题目,就可以使用做第一题使用的方法甚至说代码都可以直接套用。但是不同的一点在于,第一题得到的三元组可以重复,但是这一题不可以,所以我们要进行去重,在找到符合条件的三元组后left和right指针移动之后要判断该位置元素和前一个是否相同,如果相同就直接跳过不同就可以继续进行处理,当然这里的跳过过程要注意越界的问题。我们对于固定的第三个数也要进行去重,道理也是一样,就是i进行移动后,要判断当前位置元素和前一个是否相同,如果相同直接跳过,这样就完成了去重。
代码如下:

class Solution {
    public List<List<Integer>> threeSum(int[] nums) {
        int n = nums.length;
        Arrays.sort(nums);
        List<List<Integer>> retList = new ArrayList<>();

        for (int i = n - 1; i >= 2; i--) {
            int left = 0;
            int right = i - 1;
            while (right > left) {
                int sum = nums[left] + nums[right];
                if (sum > -nums[i]) {
                    right--;
                } else if (sum < -nums[i]) {
                    left++;
                } else {
                    retList.add(new ArrayList(Arrays.asList(nums[left], nums[right], nums[i])));
                    left++;
                    right--;
                    while (left < right && nums[left] == nums[left - 1]) {
                        left++;
                    }
                    while (right > left && nums[right] == nums[right + 1]) {
                        right--;
                    }
                }
            }
            while (i > 1 && nums[i] == nums[i-1]) {
                i--;
            }
        }
        return retList;
    }
}

题目链接

4. 四数之和(18)

题目描述:
在这里插入图片描述

算法原理:
这题和上一题三数之和就是一致的,但是就是这里要多套一层循环去多固定一个数,也就是通过两层循环固定两个数分别为nums[i]和nums[j],然后根据题意nums[left]+nums[right]需要满足target-nums[i]-nums[j]这样的条件。另外就是也需要去重,相比三数之和就是多对一层循环去一次重。
代码如下:

class Solution {
    public List<List<Integer>> fourSum(int[] nums, int target) {
        List<List<Integer>> list = new ArrayList();
        Arrays.sort(nums);
        int n = nums.length;
        for (int i = n - 1; i > 2;) {
            for (int j = i - 1; j > 1;) {
                int left = 0;
                int right = j - 1;
                long aim =  (long)target - nums[i] - nums[j];
                while (left < right) {
                    int temp = nums[left] + nums[right];
                    if (temp > aim) {
                        right--;
                    } else if (temp < aim) {
                        left++;
                    } else {
                        list.add(new ArrayList(Arrays.asList(nums[left], nums[right], nums[j], nums[i])));
                        left++;
                        right--;
                        while (left < right && nums[left - 1] == nums[left]) {
                            left++;
                        }
                        while (left < right & nums[right + 1] == nums[right]) {
                            right--;
                        }
                    }
                }
                j--;
                while (j > 1 && nums[j + 1] == nums[j]) {
                    j--;
                }
            }
            i--;
            while (i > 2 && nums[i + 1] == nums[i]) {
                i--;
            }
        }
        return list;
    }
}

题目链接

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

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

相关文章

单元测试很难么?

前言 你可能会用单元测试框架&#xff0c;python的unittest、pytest&#xff0c;Java的Junit、testNG等。 那么你会做单元测试么&#xff01;当然了&#xff0c;这有什么难的&#xff1f; test_demo.py def inc(x): return x 1 def test_answer(): assert inc(3) 4 i…

【计算机毕业设计】211校园约拍微信小程序

&#x1f64a;作者简介&#xff1a;拥有多年开发工作经验&#xff0c;分享技术代码帮助学生学习&#xff0c;独立完成自己的项目或者毕业设计。 代码可以私聊博主获取。&#x1f339;赠送计算机毕业设计600个选题excel文件&#xff0c;帮助大学选题。赠送开题报告模板&#xff…

行为树行为树行为树

行为树由一个个节点组成 结构&#xff1a;树状结构运行流程&#xff1a;从根节点开始自顶向下往下遍历&#xff0c;每经过一个节点就执行节点对应的功能。 我们规定&#xff0c;每个节点都提供自己的excute函数&#xff0c;返还执行失败/成功结果。 然后根据不同节点的执行结…

从0到1使用vite搭建react项目保姆级教程(持续更新中)

一、vite创建react项目 要使用Vite创建一个React项目&#xff0c;你需要按照以下步骤操作&#xff1a; 1、确保你已经安装了Node.js&#xff08;建议使用最新的稳定版本&#xff09;。 2、 使用npm命令安装Vite CLI工具&#xff0c;再来创建项目 npm create vitelatest my-vi…

【pytorch01】简单回归问题

1.梯度下降&#xff08;Gradient Descent&#xff09; y x 2 ∗ s i n ( x ) yx^{2}*sin(x) yx2∗sin(x) y ′ 2 ∗ x ∗ s i n ( x ) x 2 ∗ c o s ( x ) y2*x*sin(x) x^{2}*cos(x) y′2∗x∗sin(x)x2∗cos(x) 求最小值要求导 梯度下降定义&#xff1a;梯度下降要迭代计…

矿用行程位移传感器传感器ZE0701-06CU

矿用行程传感器概述 矿用行程传感器是一种专为煤矿等特定环境设计的传感器&#xff0c;用于监测和测量设备或部件的位移量。它们通常用于液压支架、千斤顶、掘进机等矿山设备中&#xff0c;帮助监测和控制设备的运动状态&#xff0c;以确保安全和高效的生产。 定义和功能 矿用…

异构集成封装类型2D、2.1D、2.3D、2.5D和3D封装技术

异构集成封装类型&#xff1a;2D、2.1D、2.3D、2.5D和3D封装详解 简介随着摩尔定律的放缓&#xff0c;半导体行业越来越多地采用芯片设计和异构集成封装来继续推动性能的提高。这种方法是将大型硅芯片分割成多个较小的芯片&#xff0c;分别进行设计、制造和优化&#xff0c;然后…

算法金 | 再见!!!梯度下降(多图)

大侠幸会&#xff0c;在下全网同名「算法金」 0 基础转 AI 上岸&#xff0c;多个算法赛 Top 「日更万日&#xff0c;让更多人享受智能乐趣」 接前天 李沐&#xff1a;用随机梯度下降来优化人生&#xff01; 今天把达叔 6 脉神剑给佩奇了&#xff0c;上 吴恩达&#xff1a;机器…

Python接口测试实战之搭建自动化测试框架

&#x1f345; 视频学习&#xff1a;文末有免费的配套视频可观看 &#x1f345; 点击文末小卡片&#xff0c;免费获取软件测试全套资料&#xff0c;资料在手&#xff0c;涨薪更快 一.数据分离:从Excel中读取数据 之前的用例中&#xff0c;数据直接写在代码文件里&#xff0c;不…

OpenAI新模型发布,免费开放GPT-4o!但只开放一点点...

GPT-4o 中的“o”代表“omni”——指的是 GPT-4o 的多模态。 该模型将向免费客户开放&#xff0c;这意味着任何人都可以通过 ChatGPT 访问 OpenAI 最先进的技术。 GPT-4o 是 OpenAI 昨天晚上发布的新旗舰模型&#xff0c;可以实时推理音频、视觉和文本。 据官方介绍&#xff0…

椭圆的标准方程与协方差矩阵的特征值和特征向量的关系

椭圆的标准方程与协方差矩阵的特征值和特征向量的关系 flyfish 单位圆 &#xff1a;单位圆表示在标准正交基下的分布。 椭圆 &#xff1a;通过协方差矩阵的特征向量和特征值变换得到的椭圆&#xff0c;表示数据在新的坐标系下的分布。 特征向量 &#xff1a;红色箭头表示特征…

【C语言】一维数组(详解)

目录 1. 数组的概念 2. 一维数组的创建和初始化 3. 一维数组的使用 4. 一维数组在内存中的存储 5. sizeof 计算数组元素个数 正文开始—— 1. 数组的概念 数组是一组相同类型元素的集合。 数组中存放的是1个或者多个数据&#xff0c;但是数组元素个数不能为0。…

运算放大器(运放)同相放大器电路

设计目标 输入电压ViMin输入电压ViMax输出VoMin输出VoMax电源Vcc电源Vee-1V1V-10V10V15V–15V 设计说明 这种设计将输入信号 Vi 放大&#xff0c;信号增益为 10V/V。输入信号可能来自高阻抗源&#xff08;例如 MΩ&#xff09;&#xff0c;因为该电路的输入阻抗由运算放大器…

vue3delete请求报403forbidden,前后端解决方式,cookie无效问题

在做开发时&#xff0c;前期已经在Controller类加上CrossOrigin(origins "*")&#xff0c;发送get和post请求都没问题&#xff0c;但遇到delete请求时&#xff0c;又报出跨域问题 一.前端添加proxy代理服务器&#xff08;未能解决&#xff09; 在vue.config.js中使…

PHP转Go系列 | 字符串的使用姿势

大家好&#xff0c;我是码农先森。 输出 在 PHP 语言中的输出比较简单&#xff0c;直接使用 echo 就可以。此外&#xff0c;在 PHP 中还有一个格式化输出函数 sprintf 可以用占位符替换字符串。 <?phpecho 码农先森; echo sprintf(码农:%s, 先森);在 Go 语言中调用它的输…

pikachu靶场之XSS漏洞测试

一、环境配置 1.pikachu官网下载 下载地址&#xff1a;https://github.com/zhuifengshaonianhanlu/pikachu 2.百度网盘&#xff08;里面含有pikachu跟phpstudy&#xff09; 链接&#xff1a;pikachu下载 密码&#xff1a;abcd 配置&#xff1a;pikachu下载及安装-图文详解…

14K屏FPGA通过MIPI接口点亮

一、屏参数 屏分辨率为13320*5120&#xff0c;MIPI接口8 LANE。 二、驱动接口电路 屏偏置电压5.5V&#xff0c;逻辑供电1.8V。8 LANE MIPI&#xff0c;2 PORT。 三、MIPI DSI规范 DCS (Display Command Set)&#xff1a;DCS是一个标准化的命令集&#xff0c;用于命令模式的显…

基于单片机的智能窗户控制系统的设计

摘 要&#xff1a; 根据单片机技术和现代传感器技术 &#xff0c; 本文主要针对基于单片机的智能窗户控制系统的设计进行探讨 &#xff0c; 仅供参考 。 关键词&#xff1a; 单片机 &#xff1b; 智能窗户 &#xff1b; 控制系统 &#xff1b; 设计 在现代科学技术持续发展的带…

融资融券两融利率最低多少?两融利率最低账户怎么申请?

融资融券账户余额理财技巧 融资融券账户不支持货币基金申赎、逆回购等业务&#xff0c;投资者可以将资金大于维保比例300%的部分通过银证转账转出再转入到普通账户&#xff0c;参与证券公司现金理财或逆回购等业务。 融券卖出和还券技巧 融券卖出所得的资金仅能用于买券还券&…

Linux操作系统学习:day05

内容来自&#xff1a;Linux介绍 视频推荐&#xff1a;[Linux基础入门教程-linux命令-vim-gcc/g -动态库/静态库 -makefile-gdb调试]( 目录 day0530、删除用户31、添加和删除用户组创建用户组删除用户组 32、修改密码33、使用tar工具进行压缩和解压缩压缩解压缩 34、使用zip u…