力扣第十六题——最接近的三数之和

内容介绍

给你一个长度为 n 的整数数组 nums 和 一个目标值 target。请你从 nums 中选出三个整数,使它们的和与 target 最接近。

返回这三个数的和。

假定每组输入只存在恰好一个解。

示例 1:

输入:nums = [-1,2,1,-4], target = 1
输出:2
解释:与 target 最接近的和是 2 (-1 + 2 + 1 = 2) 。

示例 2:

输入:nums = [0,0,0], target = 1
输出:0

提示:

  • 3 <= nums.length <= 1000
  • -1000 <= nums[i] <= 1000
  • -104 <= target <= 104

完整代码

 class Solution {public int threeSumClosest(int[] nums, int target) {Arrays.sort(nums);int n = nums.length;int best = 10000000;for (int i = 0; i < n; ++i) {if (i > 0 && nums[i] == nums[i - 1]) {continue;}int j = i + 1, k = n - 1;while (j < k) {int sum = nums[i] + nums[j] + nums[k];if (sum == target) {return target;}if (Math.abs(sum - target) < Math.abs(best - target)) {best = sum;}if (sum > target) {int k0 = k - 1;while (j < k0 && nums[k0] == nums[k]) {--k0;}k = k0;} else {int j0 = j + 1;while (j0 < k && nums[j0] == nums[j]) {++j0;}j = j0;}}}return best;}
}

思路详解

首先搭建一个框架

  1. 排序:首先对数组进行排序,这样可以方便地使用双指针方法来寻找合适的组合。

  2. 遍历:遍历数组,对于每个元素 nums[i],使用双指针 j 和 k 在其右侧寻找另外两个数,使得这三个数的和最接近 target

  3. 双指针:在遍历过程中,j 指向 i+1k 指向数组末尾。计算 nums[i] + nums[j] + nums[k] 的和,并根据和与 target 的关系来移动指针。

  4. 去重:为了避免重复的组合,需要跳过那些重复的元素。

  5. 更新答案:在每一步中,如果找到了一个和更接近 target 的组合,就更新最佳答案 best

有了框架后我们继续一步一步解决完善代码。

1. 数组排序
Arrays.sort(nums);

首先,使用Arrays.sort方法对数组进行排序。排序是必要的,因为它使我们能够使用双指针技术来有效地找到最接近目标值的和。

2. 初始化变量
int n = nums.length;
int best = 10000000;
  • n存储数组的长度。
  • best初始化为一个很大的数,用来在后续过程中记录最接近目标值的和。
3. 遍历数组
for (int i = 0; i < n; ++i) {

通过一个for循环遍历数组中的每个元素,每个元素都将作为可能的三元组中的一个元素。

4. 跳过重复元素
if (i > 0 && nums[i] == nums[i - 1]) {continue;
}

如果当前元素与前一个元素相同,则跳过当前循环。这是为了避免重复的三元组,因为我们已经考虑了相同的第一个元素的所有可能组合。

5. 初始化双指针
int j = i + 1, k = n - 1;

对于每个i,初始化两个指针jk,分别指向i之后的元素和数组的最后一个元素。

6. 双指针搜索
while (j < k) {

while循环中,使用双指针来寻找和最接近目标值的三个数的组合。

7. 计算当前组合的和
int sum = nums[i] + nums[j] + nums[k];

计算当前三个数的和。

8. 检查是否找到了目标值
if (sum == target) {return target;
}

如果当前组合的和正好等于目标值,直接返回这个和,因为它是最接近的。

9. 更新最接近的和
if (Math.abs(sum - target) < Math.abs(best - target)) {best = sum;
}

如果当前组合的和比之前记录的最接近和更接近目标值,则更新best

10. 移动指针
if (sum > target) {int k0 = k - 1;while (j < k0 && nums[k0] == nums[k]) {--k0;}k = k0;
} else {int j0 = j + 1;while (j0 < k && nums[j0] == nums[j]) {++j0;}j = j0;
}

根据当前和与目标值的关系,移动指针jk

  • 如果当前和大于目标值,则将k向左移动以尝试找到一个更小的和。
  • 如果当前和小于目标值,则将j向右移动以尝试找到一个更大的和。
  • 在移动指针时,跳过重复的元素以避免重复的三元组。
11. 返回结果
return best;

在遍历完所有可能的组合后,返回记录的最接近目标值的和。

知识点精炼

  1. 数组排序

    • 使用Arrays.sort()方法对整数数组进行排序,为后续的双指针操作提供有序数组。
  2. 遍历数组

    • 使用for循环遍历数组元素,每个元素都作为可能的三元组中的第一个元素。
  3. 去重

    • 通过条件判断if (i > 0 && nums[i] == nums[i - 1])跳过重复元素,避免生成重复的三元组。
  4. 双指针技术

    • 在固定一个元素后,使用两个指针分别指向剩余元素的头和尾,通过比较和调整指针位置来寻找合适的组合。
  5. 求和与比较

    • 计算当前指针所指三个元素的和,并与目标值进行比较,以确定是否需要更新最接近的和。
  6. 绝对值比较

    • 使用Math.abs()函数计算与目标值的差的绝对值,以比较不同和与目标值的接近程度。
  7. 指针移动与去重

    • 根据当前和与目标值的关系移动指针,并跳过重复元素,确保每个可能的组合只被考虑一次。
  8. 边界条件处理

    • 当找到和等于目标值的组合时,立即返回目标值,因为这是最接近的情况。
  9. 返回结果

    • 在遍历完所有可能的组合后,返回记录的最接近目标值的和。
  10. 时间复杂度分析

    • 整体时间复杂度为O(n^2),其中n是数组的长度,因为外层循环是O(n),内层双指针操作是O(n)。
  11. 空间复杂度分析

    • 空间复杂度为O(log n),主要由排序算法决定,因为双指针操作是原地进行的,没有使用额外的空间。

 

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

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

相关文章

<数据集>钢板缺陷检测数据集<目标检测>

数据集格式&#xff1a;VOCYOLO格式 图片数量&#xff1a;1986张 标注数量(xml文件个数)&#xff1a;1986 标注数量(txt文件个数)&#xff1a;1986 标注类别数&#xff1a;7 标注类别名称&#xff1a;[crescent gap, silk spot, water spot, weld line, oil spot, punchin…

算法面试题五

深度学习中的优化算法&#xff1a;请列举并解释几种常用的深度学习优化算法&#xff08;如Adam、SGD等&#xff09; 深度学习中的优化算法是训练神经网络时用于最小化或最大化某个函数&#xff08;通常是损失函数或目标函数&#xff09;的重要工具。这些算法通过迭代更新模型的…

工业圆点定位激光器主要应用场景有哪些?

在现代工业生产的各个领域&#xff0c;精确定位和高效操作已成为提升生产效率和产品质量的关键。其中&#xff0c;工业圆点定位激光器以其高精度、高效率的特性&#xff0c;成为了众多工业应用中的核心工具。接下来我们就跟着鑫优威一起来深入了解一下关于工业圆点定位激光器的…

抖音/快手/小红书私信卡片在线制作

W外链平台&#xff0c;作为现代网络营销领域的一颗璀璨明星&#xff0c;其强大的功能和独特的优势已经吸引了无数企业和个人的目光。在如今这个信息爆炸的时代&#xff0c;如何有效地将自己的网站、产品、服务推广出去&#xff0c;成为了每个营销人员都在思考的问题。而W外链平…

CentOS 7报错:yum命令报错 “ Cannot find a valid baseurl for repo: base/7/x86_6 ”

参考连接&#xff1a; 【linux】CentOS 7报错&#xff1a;yum命令报错 “ Cannot find a valid baseurl for repo: base/7/x86_6 ”_centos linux yum search ifconfig cannot find a val-CSDN博客 Centos7出现问题Cannot find a valid baseurl for repo: base/7/x86_64&…

uniapp 微信默认地图选点功能实现

效果图 配置项 微信公众平台-小程序配置 uniapp配置 上代码 <template><view class"content"><button click"toMap">请选择位置</button></view> </template><script setup lang"ts">function toMa…

Flink HA

目录 Flink HA集群规划 环境变量配置 masters配置 flink-conf.yaml配置 测试 Flink HA集群规划 FLink HA集群规划如下&#xff1a; IP地址主机名称Flink角色ZooKeeper角色192.168.128.111bigdata111masterQuorumPeerMain192.168.128.112bigdata112worker、masterQuorumPee…

Leetcode1929. 数组串联

问题描述&#xff1a; 给你一个长度为 n 的整数数组 nums 。请你构建一个长度为 2n 的答案数组 ans &#xff0c;数组下标 从 0 开始计数 &#xff0c;对于所有 0 < i < n 的 i &#xff0c;满足下述所有要求&#xff1a; ans[i] nums[i]ans[i n] nums[i] 具体而言…

Unity 导入MRTK,使用URP 升级材质,MRTK的材质还是洋红色

控制台显示信息 ToggleBackground material was not upgraded. There’s no upgrader to convert Mixed Reality Toolkit/Standard shader to selected pipeline UnityEditor.Rendering.Universal.UniversalRenderPipelineMaterialUpgrader:UpgradeProjectMaterials() (at 点击…

观察者模式实战:Spring Boot中联动更新机制的优雅实现

引言 在许多应用系统中&#xff0c;我们经常需要处理多个表之间的关联更新问题。例如&#xff0c;在教育管理系统中&#xff0c;当学生的基本信息表中的年龄字段发生更改时&#xff0c;我们可能还需要同步更新学生档案表和学生成绩表中的相关信息。本文将通过一个具体的案例&a…

独立游戏《星尘异变》UE5 C++程序开发日志6——实现存档和基础设置系统

目录 一、存档类 1.创建一个SaveGame类 2.存储关卡内数据 3.加载关卡数据 4.关于定时器 5.存储全局数据 6.加载全局数据 二、存档栏 1.存档栏的数据结构 2.创建新存档 3.覆盖已有存档 4.删除存档 三、游戏的基础设置 1.存储游戏设置的数据结构 2.初始化设置 3.…

在国产芯片上实现YOLOv5/v8图像AI识别-【1.3】YOLOv5的介绍及使用(训练、导出)更多内容见视频

本专栏主要是提供一种国产化图像识别的解决方案&#xff0c;专栏中实现了YOLOv5/v8在国产化芯片上的使用部署&#xff0c;并可以实现网页端实时查看。根据自己的具体需求可以直接产品化部署使用。 B站配套视频&#xff1a;https://www.bilibili.com/video/BV1or421T74f 数据…

5.5 软件工程-系统测试

系统测试 - 意义和目的 系统测试 - 原则 系统测试 - 测试过程 系统测试 - 测试策略 系统测试 - 测试方法 真题 系统测试 - 测试用例设计 黑盒测试 白盒测试 真题 系统测试 - 调试 系统测试 - 软件度量 真题

Linux输出重定向详解

在 Linux 中&#xff0c;输出重定向是将命令的输出&#xff08;标准输出或错误输出&#xff09;重定向到文件或其他位置的过程。常见的重定向符号包括 >、>>、2> 和 &>。以下是一些常用的输出重定向操作示例&#xff1a; 标准输出重定向 使用 > 符号将命…

vue 实现打字机效果

打字机效果组件&#xff0c;支持像打字机一样模仿键入文本。支持vue 插值语法和表格等打印 ps: 灵感来着于vue-type-writer 但是 这个组件过于简单 就自己整了一个 一、预览 二、代码 组件&#xff1a; <template><div :style"{ visibility: visibility }&qu…

AI 模型本地推理 - YYPOLOE - Python - Windows - GPU - 吸烟检测(目标检测)- 有配套资源直接上手实现

Python 运行 - GPU 推理 - windows 环境准备python 代码 环境准备 FastDeploy预编译库下载 conda config --add channels conda-forge && conda install cudatoolkit11.2 cudnn8.2 pip install fastdeploy_gpu_python-0.0.0-cp38-cp38-win_amd64.whlpython 代码 impo…

虚拟机的状态更新

文章目录 虚拟机的更新一、检查虚拟机的配置1.已连接状态2. 保证镜像源挂载 二、进行更新三、其余事项 虚拟机的更新 虚拟机的更新是确保系统软件包和库的更新&#xff0c;以获得最新的修复和改进&#xff1b;如果长期没有打开单机或者集群&#xff0c;可以考虑先进行一次更新…

Artix7系列FPGA实现SDI视频编解码,基于GTP高速接口,提供3套工程源码和技术支持

目录 1、前言工程概述免责声明 2、相关方案推荐本博已有的 SDI 编解码方案本方案在Xilinx--Kintex系列FPGA上的应用本方案在Xilinx--Zynq系列FPGA上的应用 3、详细设计方案设计原理框图SDI 输入设备Gv8601a 均衡器GTP 高速接口-->解串与串化SMPTE SD/HD/3G SDI IP核BT1120转…

微软Edge浏览器全解析教程

微软Edge浏览器全解析教程 微软Edge浏览器&#xff0c;作为微软公司精心打造的一款现代化网页浏览器&#xff0c;自其首次发布以来&#xff0c;凭借其卓越的性能、出色的用户体验和不断迭代的功能&#xff0c;赢得了广大用户的青睐。本文将全面解析微软Edge浏览器的各个方面&a…

Docker容器下安装Matlab,无需挂载

Matlab的安装需要这些文件 传入ubuntu后&#xff0c;改过相关的文件权限后&#xff0c;发现还是无法挂载 这有可能是docker的安全管理策略导致容器不能挂载&#xff0c;因此采用不挂载形式&#xff0c;直接解压的方式安装Matlab 1.将iso改成zip&#xff0c;并解压 2.解压rar文件…