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:
- Elements in a quadruplet (a,b,c,d) must be in non-descending order. (ie, a ≤ b ≤ c ≤ d)
- 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)
解题思路:使用两重循环,同3sum,二分查找。注意去重。
public class Solution {
public void sort(int[] num, int start, int end){
int left=start;
int right=end;
int data=num[left];
while(left<right){
while(left<right&&num[right]>=data){
right--;
}
if(left<right){
num[left]=num[right];
}
while(left<right&&num[left]<=data){
left++;
}
if(left<right){
num[right]=num[left];
}
}
num[left]=data;
if(start<left-1){
sort(num,start,left-1);
}
if(end>left+1){
sort(num,left+1,end);
}
}
public List<List<Integer>> fourSum(int[] num, int target) {
List<List<Integer>> rs=new ArrayList<List<Integer>>();
int sum=0;
int len=num.length;
if(num==null){
return null;
}
if(len<4){
return rs;
}
sort(num,0,len-1);
for(int i=0;i<=len-4;i++){
int j=i+1;
while(j<=len-3){
sum=num[i]+num[j];
int left=j+1;
int right=len-1;
while(left<right){
int diff=num[left]+num[right]+sum;
if(diff>target){
right--;
}else if(diff<target){
left++;
}else{
List<Integer> data=new ArrayList<Integer>();
data.add(num[i]);
data.add(num[j]);
data.add(num[left]);
data.add(num[right]);
if(!rs.contains(data)){
rs.add(data);
}
left++;
right--;
}
}
j++;
}
}
return rs;
}
}
public void sort(int[] num, int start, int end){
int left=start;
int right=end;
int data=num[left];
while(left<right){
while(left<right&&num[right]>=data){
right--;
}
if(left<right){
num[left]=num[right];
}
while(left<right&&num[left]<=data){
left++;
}
if(left<right){
num[right]=num[left];
}
}
num[left]=data;
if(start<left-1){
sort(num,start,left-1);
}
if(end>left+1){
sort(num,left+1,end);
}
}
public List<List<Integer>> fourSum(int[] num, int target) {
List<List<Integer>> rs=new ArrayList<List<Integer>>();
int sum=0;
int len=num.length;
if(num==null){
return null;
}
if(len<4){
return rs;
}
sort(num,0,len-1);
for(int i=0;i<=len-4;i++){
int j=i+1;
while(j<=len-3){
sum=num[i]+num[j];
int left=j+1;
int right=len-1;
while(left<right){
int diff=num[left]+num[right]+sum;
if(diff>target){
right--;
}else if(diff<target){
left++;
}else{
List<Integer> data=new ArrayList<Integer>();
data.add(num[i]);
data.add(num[j]);
data.add(num[left]);
data.add(num[right]);
if(!rs.contains(data)){
rs.add(data);
}
left++;
right--;
}
}
j++;
}
}
return rs;
}
}