力扣:18.四数之和

一、做题链接:18. 四数之和 - 力扣(LeetCode)

二、题目分析

1.做这一道题之前本博主建议先看上一篇《三数之和》

2.题目分析

给你一个由 n 个整数组成的数组 nums ,和一个目标值 target 。请你找出并返回满足下述全部条件且不重复 的四元组 [nums[a], nums[b], nums[c], nums[d]] (若两个四元组元素一一对应,则认为两个四元组重复):

  • 0 <= a, b, c, d < n
  • abcd 互不相同
  • nums[a] + nums[b] + nums[c] + nums[d] == target

你可以按 任意顺序 返回答案 。

示例 1:

复制代码
输入:nums = [1,0,-1,0,-2,2], target = 0
输出:[[-2,-1,1,2],[-2,0,0,2],[-1,0,0,1]]

示例 2:

复制代码
输入:nums = [2,2,2,2,2], target = 8
输出:[[2,2,2,2]]

由题可知:做这个题要主要面临的困难是去重和漏选,去重主要利用的是排序,set等,漏选就枚举

示例解析1,0,-1,0,-2,2->排序后-2,-1,0,0,1,2

以此类推得出最终答案

三、算法分析

1.暴力枚举法:排序+四层for循环+set去重;时间复杂度O(n^4)-----》这个不可跑过力扣

2.双指针+单调性+两层for循环;时间复杂度O(n^3)-》利用率三数之和--》利用率两数之和

算法步骤:

1.排序

2.设置第一个固定数

3.设置第二个固定数

4.两数之和,设置两个指针left,right-》降低复杂度的关键

5.细节处理,重点关注去重问题

注意事项:

去重:1.去除第一固定数的重如:0,0,求出来的一样

2.去除第二个数的重如:第一固定数是-1,第二固定数:0,0结果一样

3.去除两数之和的重

四、代码编写

java 复制代码
 public List<List<Integer>> fourSum(int[] nums, int target) {
        Arrays.sort(nums);//排序
        List<List<Integer>> Foursum = new ArrayList<>();
        for (int i = 0; i < nums.length; )//固定一个数
        {
            for (int j = i + 1; j < nums.length;)//固定第二个数
            {

                long tar = (long) target - nums[i] - nums[j];//求出两数之和的目标
                List<Integer> list = new ArrayList<>();
                //两数之和
                int left = j + 1;
                int right = nums.length - 1;
                while (left < right) {
                    if (left < nums.length && nums[left] + nums[right] < tar) {
                        left++;
                    } else if (right > 0 && nums[left] + nums[right] > tar) {
                        right--;
                    } else {
                        list.add(nums[i]);
                        list.add(nums[j]);
                        list.add(nums[left]);
                        list.add(nums[right]);
                        Foursum.add(list);
                        //去除第三重
                        while (left < nums.length && nums[left] == list.get(2)) {
                            left++;
                        }
                        while (right > 0 && nums[right] == list.get(3)) {
                            right--;
                        }
                    }
                }
                //去除第二重
                j++;
                while (j < nums.length && nums[j] == nums[j - 1]) {
                    j++;
                }
            }
            //去除第三重
            i++;
            while (i<nums.length && nums[i]==nums[i-1])
            {
                i++;
            }
        }
        return Foursum;
    }

你学废了吗

相关推荐
leo__52018 小时前
随机接入退避算法过程模拟实现
网络·算法
-To be number.wan18 小时前
算法日记 | STL- sort排序
c++·算法
玖釉-18 小时前
Vulkan 中 Shader 的 vert、frag、mesh、comp 全面解析:作用、关系、特点与工程实践
开发语言·c++·windows·算法·图形渲染
智者知已应修善业18 小时前
【51单片机2个外部中断切换LED花样】2024-1-3
c++·经验分享·笔记·算法·51单片机
8Qi818 小时前
LeetCode 31:下一个排列(Next Permutation)—— 完整题解笔记 ✅
笔记·算法·leetcode·指针·思维·排列
春日见18 小时前
五分钟入门强化学习DDPG
大数据·人工智能·算法·机器学习·计算机视觉
vivo互联网技术18 小时前
ICLR 2026 | LiveMoments 用参考图引导的扩散模型提升重选封面帧画质
人工智能·算法·aigc技术探索
落羽的落羽19 小时前
【算法札记】练习 | Week5
linux·服务器·c++·人工智能·计算机网络·算法·哈希算法
玖釉-19 小时前
编辑距离(Edit Distance)——从字符串相似度到动态规划经典模型
算法·leetcode·动态规划