15. 3Sum
Medium
Given an array nums
of n integers, are there elements a, b, c in nums
such that a + b + c = 0? Find all unique triplets in the array which gives the sum of zero.
Note:
The solution set must not contain duplicate triplets.
Example:
Given array nums = [-1, 0, 1, 2, -1, -4],
A solution set is:
[
[-1, 0, 1],
[-1, -1, 2]
]
题目链接:https://leetcode.com/problems/3sum/
这道题是1. Two Sum的升级版,3个数相加为指定和。
常规思路是按照2数和的方法,排序,固定一个数字,找剩余2数和为指定数的组合。特别的,由于本题指定和为0,说明满足要求的3个数要么全为0,要么有正有负,因此在固定数字的遍历时,可以只需要遍历非正的(或者非负),就能找到所有解。
去重的几个点:
1)相同固定数字得到的解一样,直接跳过;
2)同一固定数字已找到一个解,继续找是否有别的解时,要先跳过与当前解相同的数字。
代码:
class Solution {
public:
vector<vector<int>> threeSum(vector<int>& nums) {
vector<vector<int>> res;
int len = nums.size();
if (len <= 0) return {};
sort(nums.begin(), nums.end());
int i = 0;
while (i < len && nums[i] <= 0){
if (i > 0 && nums[i] == nums[i - 1]){
++i;
continue;
}
int target = 0 - nums[i];
int j = i + 1, k = len - 1;
while (j < k){
if (nums[j] + nums[k] == target){
res.push_back({nums[i], nums[j], nums[k]});
while (j < k && nums[j] == nums[j + 1]) ++j;
while (j < k && nums[k] == nums[k - 1]) --k;
++j;
--k;
}else if(nums[j] + nums[k] > target) --k;
else ++j;
}
++i;
}
return res;
}
};
关于双指针的小tip:
找组合的题和找区间类似,双指针能降低时间复杂度。数字组合通常要排序来辅助。
本题c++ vector的tip:
vector的初始化可以为
std::vector<type> name {value1, value2, ...};
本题里直接将匿名初始化的vector加入大vector集中。
类似思想的题: