题解 | #数组中相加和为0的三元组#

数组中相加和为0的三元组

http://www.nowcoder.com/practice/345e2ed5f81d4017bbb8cc6055b0b711

超级详细的题解与代码备注:(C++代码)
思路:
首先判断给点数组的大小是否<3 小于3的话则直接返回一个空的结果.
对整个数组进行排序:
寻找一个基准值target(基准值为从数组的第1个元素到倒数第三个元素),然后再从基准值target的后面找到两个数组等于-target,这个时候是不是就是求两数之和啦。
好的,那这个时候利用双指针解法,代码上都有详细备注,我相信大家肯定都能看懂的。

class Solution {
public:
    vector<vector<int> > threeSum(vector<int>& num) {
        vector<vector<int>> ans;
        if (num.size() < 3) //个数不满足的时候明显不符合要求,返回结果。
            return ans;
        sort(num.begin(), num.end()); //对给定的数组进行排序

        for (int i = 0; i < num.size() - 2; i++) //-2是因为保证从i开始剩下的数组长度>=3
        {
            if (num[i] > 0)       //基准值大于0 ,后面查找的两个数肯定不存在。
                break;
            int j = i+1, k = num.size() - 1; //j从i后面的第一个数开始尝试,k从数组最后一个位置开始尝试
            int target = -num[i];     //寻找两个数相加为target
            while (j<k)
            {
                if (num[j] + num[k] < target) //说明寻找的两个数比目标值小,所以尝试更大的一种情况。
                    j++;
                else if (num[j] + num[k] > target)//说明比目标值大,尝试更小的一种情况
                    k--;
                else                       //相等的状况。
                {
                    vector<int> temp = {num[i],num[j],num[k]};
                    ans.push_back(temp);
                    //target=num[j]+num[k]   target一定时,确定了num[j]、num[k] 其中一个那么另外一个就确定了  那么得到的肯定就会重复
                    //所以下面两行代码是为了去掉当target一定时 重复的情况
                    while (num[j] == num[j + 1] && j+1<k)    j++; 
                    while (num[k] == num[k - 1] && k-1>j)  k--;
                    ++j; --k;      //相等的话这两个数就不再使用了(已经用过了)。
                }
            }
            //为了去除target重复的情况,试想一下,当num[i]=x的时候, i后面所有相加=-x 的两个数已经全部求出来了。
            //那再求i+1 后面的必然是上面所求的子集。 这里依旧还是需要判断i,因为防止后面再次判断num[i+1]的时候产生越界。
            while (num[i] == num[i + 1] && i < num.size() - 2)   i++;
        }
        return ans;

    }
};
全部评论

相关推荐

评论
4
1
分享
牛客网
牛客企业服务