LeetCode 015 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 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)
分析:
参考链接:http://blog.csdn.net/zhouworld16/article/details/16917071
2Sum:http://www.cnblogs.com/510602159-Yano/p/4242664.html
求解3个数的和,需要O(n2);去重,需要O(n);
① 对数组进行排序;
② i从0到n-1,对num[i]求另外两个数,这里用p和q;
③ p指向i+1,q指向结尾。sum = num[i] + num[p]+ num[q];
④ 利用加逼定理求解,终止条件是p == q;
⑤ 顺带去重。
去重时:
① 如果i到了i+1,num[i] == num[i - 1],则求出的解肯定重复了;
② 如果p++,num[p] = num[p + 1],则求出的解肯定重复了。
代码如下:
class Solution { public: void InsertSort(vector<int> &a, int n){ int temp; for (int i = 1; i < n; ++i){ temp = a[i]; int j; for (j = i; j > 0 && temp < a[j - 1]; --j) { a[j] = a[j - 1]; } a[j] = temp; } } vector<vector<int> > threeSum(vector<int> &num) { vector<vector<int>> result; //小于3个数,则返回 if(num.size() < 3) return result; //对原数组非递减(递增)排序 InsertSort(num, num.size()); int sum = 0; for(int i = 0; i < num.size(); i++){ //去重 if(i != 0 && num[i] == num[i-1]) continue; int p = i + 1, q = num.size() - 1; //收缩法寻找第2,第3个数 while(p < q){ sum = num[i] + num[p] + num[q]; if(sum == 0){ vector<int> newRes; newRes.push_back(num[i]); newRes.push_back(num[p]); newRes.push_back(num[q]); InsertSort(newRes,newRes.size()); result.push_back(newRes); //寻找其他可能的2个数,顺带去重 while (++p < q && num[p-1] == num[p]); while (--q > p && num[q+1] == num[q]); } //和太小,p向后移动 else if(sum < 0) p++; //和过大,q向前移动 else q--; } } return result; } };