三数之和(LeetCode 15)

文章目录

  • 1.问题描述
  • 2.难度等级
  • 3.热门指数
  • 4.解题思路
    • 方法一:暴力法
    • 方法二:排序+双指针
  • 5.实现示例
  • 参考文献

1.问题描述

给你一个整数数组 nums,判断是否存在三元组 [nums[i], nums[j], nums[k]] 满足 i != j、i != k 且 j != k ,同时还满足 nums[i] + nums[j] + nums[k] == 0 。

请你返回所有和为 0 且不重复的三元组。

注意: 答案中不可以包含重复的三元组。

示例 1:

输入:nums = [-1,0,1,2,-1,-4]
输出:[[-1,-1,2],[-1,0,1]]
解释:
nums[0] + nums[1] + nums[2] = (-1) + 0 + 1 = 0 。
nums[1] + nums[2] + nums[4] = 0 + 1 + (-1) = 0 。
nums[0] + nums[3] + nums[4] = (-1) + 2 + (-1) = 0 。
不同的三元组是 [-1,0,1] 和 [-1,-1,2] 。
注意,输出的顺序和三元组的顺序并不重要。

示例 2:

输入:nums = [0,1,1]
输出:[]
解释:唯一可能的三元组和不为 0 。

示例 3:

输入:nums = [0,0,0]
输出:[[0,0,0]]
解释:唯一可能的三元组和为 0 。

2.难度等级

Medium。

3.热门指数

★★★★☆

出题公司:阿里、腾讯、字节。

4.解题思路

方法一:暴力法

暴力法应该是我们最先想到的方法。

三层循环枚举三元组,时间复杂度很高为 O ( n 3 ) O(n^3) O(n3)

在这之后,我们还需要使用哈希表进行去重操作,得到不包含重复三元组的最终答案,还会消耗了大量的空间。

考虑到三元组中元素的顺序可能不同,为了去重,我们可以先对三元组进行排序。如何唯一表示三元组并将其写入哈希表呢?

我们可以将三元组元素拼成一个字符串写入哈希表,然后遍历所有三元组,去掉重复的三元组。

暴力法的时间复杂度和空间复杂度都很高,因此我们要换一种思路来考虑这个问题。

方法二:排序+双指针

首先题目要求结果不包含重复三元组,而在给出的 nums 中又可能出现重复的元素。

大多数避免重复的问题,思路一般是排序。因此可以先对 nums 进行一次排序,这样做的意义一是方便使用双指针,二是遍历中也方便跳过重复项。

那么应该怎样找出三个相加为 0 的三元组呢?具体步骤如下:

  1. 将数组 nums 升序排序。
  2. 遍历数组,将 nums[i] 作为三元组的第一个元素。
  3. 在数组剩下的数中使用双指针 j 和 k 分别指向首尾。
  4. 判断 nums[i]、nums[j] 和 nums[k] 的和是否为零,如果为零,则保留下来。然后移动指针 j 和 k 直到二者相遇。

在这里插入图片描述

关于指针 j 和 k 的移动规则:

1.如果和为零,那么需要同时移动 j 和 k。j 往右移,k 往左移。
2.如果和小于零,那么需要提高 nums[j] 的值,所以 j 往右移,k 不动。
3.如果和大于零,那么需要减小 nums[k] 的值,所以 k 往左移,j 不动。
4.j 在左移 和 k 在右移后,与前一项可能相同,那么就需要继续移动。

关于数组的遍历规则:

1.遍历数组的次数不是整个数组的长度,只需要遍历至倒数第 3 个元素,因为是考察 3 个元素的和
2.当 nums[i] 大于 0 的时候,后面所有的三元组都不满足条件,结束遍历并返回结果。
3.当 nums[i] 与前一个数相同时,跳过本次循环。

复杂度分析:

时间复杂度:双指针移动的复杂度是 O(n),再加上外能循环的复杂度 O(n),所以总的时间复杂度是 O ( n 2 ) O(n^2) O(n2)

空间复杂度:我们忽略存储答案的空间,那么空间复杂度是 O(1)。

5.实现示例

下面以 Golang 为例,给出「排序+双指针」的实现。

import (
	"golang.org/x/exp/slices"
)

func threeSum(nums []int) [][]int {
    slices.Sort(nums)
    var r [][]int
    var j, k int
    for i:=0; i < len(nums)-2; i++{
        // 跳过相同的数。
        if i > 0 && nums[i] == nums[i-1] {
            continue
        }
        // 双指针移动。
        j, k = i+1, len(nums)-1
        for j < k {
            if nums[i] + nums[j] + nums[k] == 0 {
                r = append(r, []int{nums[i], nums[j], nums[k]})
                // 同时移动左右指针。
                j++
                for j < k && nums[j] == nums[j-1] {
                    j++
                }
                k--
                for j < k && nums[k] == nums[k+1] {
                    k--
                }
            } else if nums[i] + nums[j] + nums[k] < 0 {
                // 移动左指针。
                j++
                for j < k && nums[j] == nums[j-1] {
                    j++
                }
            } else {
                // 移动右指针。
                k--
                for j < k && nums[k] == nums[k+1] {
                    k--
                }
            }
        }
    }
    return r
}

参考文献

15. 三数之和 - LeetCode
LeetCode题解- 题目:三数之和

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

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

相关文章

P1单片机定时器配置及定时器中断——C51(超详细)

目录 1. 简介 1.1 概念解读 1.2 定时器怎么定时 1.什么是晶振 2.什么是时钟周期 3.什么是机器周期 4.加1经过了多少时间 1.3 定时器编程 1.如何算出10ms定时器的初值(TL0 TH0) 2.关于TCON ,怎么知道爆表 3.怎么开始计时(TR0) 4.定时器使用是有很多种模式的&#xf…

Gerrit的使用

项目存储配置 为了能够模拟开发人员和审核人员两个角色&#xff0c;需要有1台服务器模拟操作提交和审核 登陆linux服务器账户&#xff0c;并生成id_rsa.pub 添加git配置 Git配置一般存储的是name 和 email地址 这里的email地址需要和gerrit系统的账号的email地址一致&#…

佛山陶企再造行业新风口,开启中国陶瓷下半场

近年来&#xff0c;消费形态逐渐呈现年轻化、时尚化、数字化的趋势&#xff0c;新一地居住者对于居住环境的品质和舒适度要求日益提高。伴随着新消费势力的崛起&#xff0c;家居建材行业消费转型升级已成必然。“千年陶都”佛山作为我国陶瓷行业的风向标&#xff0c;率先推进技…

SD-WAN组网案例分享——简单高效的远程视频监控方案

在网络化和信息化建设的推动下&#xff0c;远程视频监控设备的应用范围已经不再局限于政府部门和金融行业。中小企业对远程视频监控设备的需求也在持续增长。 案例背景 本次案例分享的是一家大型制造业企业&#xff0c;该企业拥有遍布全国各地的生产厂房和仓库。然而&#xff…

GPS定位与IP地址定位的差异及应用场景

随着科技的不断发展&#xff0c;定位技术在日常生活和商业应用中变得越来越普遍。在定位技术中&#xff0c;GPS&#xff08;全球定位系统&#xff09;和IP地址定位是两种常见的方法。本文将探讨GPS定位与IP地址定位的差异以及它们在不同应用场景中的应用。 1. GPS定位 a. 工作…

flink-1.17.2的单节点部署

flink 简介 Apache Flink 是一个开源的流处理和批处理框架&#xff0c;用于大数据处理和分析。它旨在以实时和批处理模式高效处理大量数据。Flink 支持事件时间处理、精确一次语义、有状态计算等关键功能。 以下是与Apache Flink相关的一些主要特性和概念&#xff1a; 流处理…

故障注入测试有哪些多重作用?

在软件开发的世界中&#xff0c;保证系统的鲁棒性和稳定性至关重要。为了应对各种潜在的故障和异常情况&#xff0c;测试团队采用了各种测试方法&#xff0c;其中之一就是故障注入测试。这种测试方法的目标是有目的地向系统引入故障&#xff0c;以评估系统在面对异常情况时的表…

响应式编程一之基础夯实(初学必看!)

响应式编程一之基础夯实&#xff08;初学必看&#xff01;&#xff09; 函数式编程常见lambda表达式求一个数组里面的最小值代码简洁的函数式编程返回指定对象的接口实例JDK8 新特性jdk8函数式接口predicate 判断hashmap是否为空consumer总结方法引用示例lambda表达式的类型推断…

解题方式篇-回溯

回溯算法 1、简介 简介&#xff1a;回溯法也可以叫做回溯搜索法&#xff0c;它是一种搜索的方式。 回溯是递归的副产品&#xff0c;只要有递归就会有回溯。回溯是一种暴力的搜索方式。 回溯法&#xff0c;一般可以解决如下几种问题&#xff1a;组合&#xff08;无序&#xff0…

西南科技大学数字电子技术实验五(用计数器设计简单秒表)预习报告

一、计算/设计过程 说明&#xff1a;本实验是验证性实验&#xff0c;计算预测验证结果。是设计性实验一定要从系统指标计算出元件参数过程&#xff0c;越详细越好。用公式输入法完成相关公式内容&#xff0c;不得贴手写图片。&#xff08;注意&#xff1a;从抽象公式直接得出结…

Keil 编译输出信息分析:Program size: Code, RO-data , RW-data, ZI-data

一般 MCU 包含的存储空间有&#xff1a;片内 Flash 与片内 RAM&#xff0c;RAM 相当于内存&#xff0c;Flash 相当于硬盘。编译器会将一个程序分类为好几个部分&#xff0c;分别存储在 MCU 不同的存储区。 如图所示&#xff0c;在Keil中编译工程成功后&#xff0c;在下面的Bul…

AI+无代码助力企业供应链优化

内容来自演讲&#xff1a;潘峰 | 预见明日科技&#xff08;北京&#xff09;有限公司 | CEO 摘要 本文介绍了企业供应链中的挑战和解决方案。文章指出&#xff0c;供应链成本占企业经营成本的大部分&#xff0c;且存在供给端和需求端的高度不确定性。为应对这种不确定性&…

Embedding压缩之基于二进制码的Hash Embedding

推荐系统中&#xff0c;ID类特征的表示学习&#xff08;embedding learning&#xff09;是深度学习模型成功的关键&#xff0c;因为这些embedding参数占据模型的大部分体积。这些模型标准的做法是为每一个ID特征分配一个unique embedding vectors&#xff0c;但这也导致存储emb…

【QT 5 调试软件+(Linux下验证>>>>串口相关初试串口)+Windows下qt代码在Linux下运行+参考win下历程+基础样例】

【QT 5 调试软件Linux下验证>>>>串口相关初试串口参考win下历程基础样例】 1、前言2、实验环境3、先行了解4、自我总结-win下工程切到Linux下1、平台无关的代码&#xff1a;2、依赖的库&#xff1a;3、文件路径和换行符&#xff1a;4、编译器差异&#xff1a;5、构…

揭秘高效大型语言模型:技术、方法与应用展望

近年来&#xff0c;大型语言模型&#xff08;LLMs&#xff09;在自然语言处理领域取得了显著的进展&#xff0c;如GPT-series(GPT-3, GPT-4)、Google-series(Gemini, PaLM), Meta-series(LLAMA1&2), BLOOM, GLM等模型在各种任务中展现出惊人的能力。然而&#xff0c;随着模…

IDC报告:国内游戏云市场,腾讯云用量规模位列第一

12月12日消息&#xff0c;IDC公布最新的《中国游戏云市场跟踪研究&#xff0c;2022H2》报告&#xff08;以下简称“《报告》”&#xff09;显示&#xff0c;腾讯云凭借全球化节点布局以及国际领先的游戏技术积累&#xff0c;在整体规模、云游戏流路数、CDN流量峰值带宽等多维度…

C++笔记之Delegate和委托构造(Delegating constructor)

C笔记之Delegate和委托构造辨析 code review! —— 杭州 2023-12-10 参考博文&#xff1a;C笔记之文档术语——将可调用对象作为函数参数 文章目录 C笔记之Delegate和委托构造辨析0.有道词典&#xff1a;英语发音1.ChatGPT&#xff1a;delegate概念详解2.Delegate和“将可调…

Python异常、模块和包

Python异常、模块和包 1.了解异常2.异常的捕获方法3.异常的传递4.Python模块5.Python包 1.了解异常 1.1什么是异常 当检测到一个错误是&#xff0c;Python解释器就无法继续执行了&#xff0c;发而出现了一些错误提示&#xff0c;这就是所谓的“异常”&#xff0c;也就是我们常…

橡胶塑料企业网站建设的作用是什么

橡胶塑料产品一般属于大额交易&#xff0c;对企业来说&#xff0c;需要不断提升品牌和拓客&#xff0c;但如今线下信息传播力不足&#xff0c;难以全面呈现内容&#xff0c;需要商家不断提升线上能力&#xff0c;获得进一步发展。 1、品牌宣传展示难 线上没有自己的平台难以将…

HTML---列表.表格.媒体元素

文章目录 前言一、pandas是什么&#xff1f;二、使用步骤 1.引入库2.读入数据总结 一.列表 无序列表 HTML中的无序列表&#xff08;Unordered List&#xff09;用于显示一组项目&#xff0c;每个项目之前没有特定的顺序或编号。无序列表使用<ul>标签来定义&#xff0c;每…