4Sum
题目
Given an array S of n integers, are there elements a,b,c, and d in S such that a+b+c+d= target? Find all unique quadruplets in the array which gives the sum of target.
Note:The solution set must not contain duplicate quadruplets.
For example, given array S = [1, 0, -1, 0, -2, 2], and target = 0.
A solution set is:
[
[-1, 0, 0, 1],
[-2, -1, 1, 2],
[-2, 0, 0, 2]
]
解析
问题一:
为何第一个for loop的查重 if 条件是 i>0 , 第二个for loop的查重 if 条件是 j>i+1因为要查重,至少保证有2个元素,比如:i = 0 和 i >0 开始查重。
思路
- two pointers method
- the first pointer named i , it start from 0 to nums.length - 3, sweeping the whole array
- meanwhile, the second pointer named j , it start from i+1 to nums.length - 2, sweeping the whole array
- For each possible first element we make a standard bi-directional 2Sum sweep of the remaining part of the array
- At the same time, we need to skip equal elements to avoid duplicates
图解
代码
class Solution {
public List<List<Integer>> fourSum(int[] nums, int target) {
List<List<Integer>> result = new ArrayList<>();
if (nums.length < 4) return result;
Arrays.sort(nums);
for (int i = 0; i < nums.length - 3; ++i) {
if (i > 0 && nums[i] == nums[i-1]) continue;
for (int j = i + 1; j < nums.length - 2; ++j) {
if (j > i+1 && nums[j] == nums[j-1]) continue;
int k = j + 1;
int l = nums.length - 1;
while (k < l) {
final int sum = nums[i] + nums[j] + nums[k] + nums[l];
if (sum < target) {
++k;
while(nums[k] == nums[k-1] && k < l) ++k;
} else if (sum > target) {
--l;
while(nums[l] == nums[l+1] && k < l) --l;
} else {
result.add(Arrays.asList(nums[i], nums[j], nums[k], nums[l]));
++k;
--l;
while(nums[k] == nums[k-1] && k < l) ++k;
while(nums[l] == nums[l+1] && k < l) --l;
}
}
}
}
return result;
}
}