[C++]LeetCode: 70 3Sum

题目:

Given an array S of n integers, are there elements a, b, c in S such that a + b + c =
0? Find all unique triplets in the array which gives the sum of zero.

Note:

  • Elements in a triplet (a,b,c) must be in non-descending order. (ie, a ≤ b ≤ c)
  • The solution set must not contain duplicate triplets.
    For example, given array S = {-1 0 1 2 -1 -4},

    A solution set is:
    (-1, 0, 1)
    (-1, -1, 2)

思路:

本题的解法类似于LeetCode: 15 3Sum Closest
(plus JAVA Code)
.也是使用先排序,后夹逼的方法求解答案。

不同的地方在于,我们需要根据第一个元素的移动(改变),不断确定新的target, 即twosum.

同时我们需要考虑如何跳过重复的集合,移动夹逼的两个左右指针时,需要进行判断移动前后元素是否相等,重复则skip。

Attention:

1. 为了不改变原来的数组,我将数组存在ivec中,再进行排序和后续操作。

//不想改变原数组,所以存在ivec中
        vector<int> ivec(num.begin(), num.end());

        if(num.size() < 3) return ret;

        sort(ivec.begin(), ivec.end());

2. 在外层大的循环下,我们不设置i++, 在循环体内判断,如果有重复数字,不断跳过。

for(int i = 0; i < ivec.size() - 2; )

//如果之间有重复的,就一直跳过
            do{
                i++;
            }while(i < ivec.size() - 1 && ivec[i-1] == ivec[i]);

3. 进行循环后,每次都需要计算 num[i]的相反数,作为target来匹配。可能存在多个匹配情况,所以即使一次匹配成功,仍然需要改变夹逼指针j 和 k,寻找其他可能的匹配组合。

int twosum = 0 - ivec[i]; //把-num[i]作为target去寻找匹配的两个数

while(j < k)
{
//即使找到第一个匹配的项,仍然需要移动坐标,寻找其他可能匹配数
   if(ivec[j] + ivec[k] == twosum)
   {
     vector<int> tmp{ivec[i], ivec[j], ivec[k]};
     ret.push_back(tmp);
     do{
         j++;
     }while(j < k && ivec[j] == ivec[j-1]);
     do{
          k--;
     }while(j < k && ivec[k] == ivec[k+1]);
    }

复杂度: O(N^2)

AC Code:

class Solution {
public:
    vector<vector<int> > threeSum(vector<int> &num) {
        vector<vector<int>> ret;
        //不想改变原数组,所以存在ivec中
        vector<int> ivec(num.begin(), num.end());

        if(num.size() < 3) return ret;

        sort(ivec.begin(), ivec.end());

        for(int i = 0; i < ivec.size() - 2; )
        {
            int j = i + 1;
            int k = ivec.size() - 1;
            int twosum = 0 - ivec[i]; //把-num[i]作为target去寻找匹配的两个数

            while(j < k)
            {
                //即使找到第一个匹配的项,仍然需要移动坐标,寻找其他可能匹配数
                if(ivec[j] + ivec[k] == twosum)
                {
                    vector<int> tmp{ivec[i], ivec[j], ivec[k]};
                    ret.push_back(tmp);
                    do{
                        j++;
                    }while(j < k && ivec[j] == ivec[j-1]);
                    do{
                        k--;
                    }while(j < k && ivec[k] == ivec[k+1]);
                }
                else if(ivec[j] + ivec[k] < twosum)
                    j++;
                else
                    k--;
            }

            //如果之间有重复的,就一直跳过
            do{
                i++;
            }while(i < ivec.size() - 1 && ivec[i-1] == ivec[i]);
        }

        return ret;
    }
};

这道题其实还可以嵌套一个twosum子程序来做。其他博文中有给出。3Sum

重点是,我们一定要注意细节的处理,就是夹逼指针的移动。

时间: 2024-12-28 10:16:52

[C++]LeetCode: 70 3Sum的相关文章

LeetCode 015 3Sum

[题目] Given an array S of n integers, are there elements a, b, c in S such that a + b + c = 0? Find all unique triplets in the array which gives the sum of zero. Note: Elements in a triplet (a,b,c) must be in non-descending order. (ie, a ≤ b ≤ c) The

LeetCode 016 3Sum Closest

[题目] Given an array S of n integers, find three integers in S such that the sum is closest to a given number, target. Return the sum of the three integers. You may assume that each input would have exactly one solution. For example, given array S = {

[Leetcode][016] 3Sum Closest (Java)

题目: https://leetcode.com/problems/3sum-closest/ [标签]Array; Two Pointers [个人分析] 这道题和它的姊妹题 3Sum 非常类似, 就不再多说了,具体一些的分析可以参考 [Leetcode][015] 3Sum 1 public class Solution { 2 public int threeSumClosest(int[] nums, int target) { 3 int result = target; 4 int

[LeetCode] 015. 3Sum (Medium) (C++/Java/Python)

索引:[LeetCode] Leetcode 题解索引 (C++/Java/Python/Sql) Github: https://github.com/illuz/leetcode 015.3Sum (Medium) 链接: 题目:https://oj.leetcode.com/problems/3sum/ 代码(github):https://github.com/illuz/leetcode 题意: 在给定数列中找出三个数,使和为 0. 分析: 先排序,再左右夹逼,复杂度 O(n*n).

[LeetCode][JavaScript]3Sum Closest

3Sum Closest Given an array S of n integers, find three integers in S such that the sum is closest to a given number, target. Return the sum of the three integers. You may assume that each input would have exactly one solution. For example, given arr

[Leetcode][015] 3Sum (Java)

题目在这里: https://leetcode.com/problems/3sum/ [标签] Array; Two Pointers [个人分析] 老实交待,这个题卡半天,第一次做不会,抄别人的.过了很久,第二次做,还是不会…….好几次都是Time Limited Error.在看过正确答案之后,才知道是用的Two Pointers + sort 做的优化. 怎么优化? 简单说,就是通过 排序 + 跳过重复(利用Two Pointers) 来达到题目中避免 duplicates的要求. 核心思

LeetCode 259. 3Sum Smaller (三数之和较小值) $

Given an array of n integers nums and a target, find the number of index triplets i, j, k with 0 <= i < j < k < n that satisfy the condition nums[i] + nums[j] + nums[k] < target. For example, given nums = [-2, 0, 1, 3], and target = 2. Retu

【Leetcode】3Sum

题目链接:https://leetcode.com/problems/3sum/ 题目: Given an array S of n integers, are there elements a, b, c in S such that a + b + c = 0? Find all unique triplets in the array which gives the sum of zero. Note: Elements in a triplet (a,b,c) must be in no

[LeetCode][JavaScript]3Sum

3Sum Given an array S of n integers, are there elements a, b, c in S such that a + b + c = 0? Find all unique triplets in the array which gives the sum of zero. Note: Elements in a triplet (a,b,c) must be in non-descending order. (ie, a ≤ b ≤ c) The