解题思路:先对原数组排序(从小到大),然后要想三个数和为0,肯定三个数不能全>0,所以只需要遍历当前值不大于0即可,然后遍历当前值的后面到最后值的和,如果三个数字和>0,则right–,如果和<0,则left++。若等于0则把当前成立的三个数保存起来继续遍历。时间复杂度O(N^2), 空间复杂度O(N^2)。
import java.util.*;
public class Solution {
public ArrayList<ArrayList<Integer>> threeSum(int[] num) {
if (num == null || num.length < 3) {
return new ArrayList<ArrayList<Integer>>();
}
ArrayList<ArrayList<Integer>> result = new ArrayList<>();
//首先对原数组排序
Arrays.sort(num);
int length = num.length;
//排完序之后只需要遍历num[i]<=0部分即可,因为>0的三个数字之和肯定>0
for (int i = 0; i < length; i++) {
if (num[i] > 0) {
break;
}
if (i != 0 && num[i] == num[i - 1]) {
//当前数组和前面一个数字一样大,说明该值遍历过了
continue;
}
int left = i + 1, right = length - 1;
while (left < right) {
if (num[i] + num[left] + num[right] > 0) {
right--;
} else if (num[i] + num[left] + num[right] < 0) {
left++;
} else {
ArrayList<Integer> list = new ArrayList<>(Arrays.asList(num[i], num[left],
num[right]));
result.add(list);
while (left < right && list.get(1) == num[left]) {
//去重
left++;
}
}
}
}
return result;
}
}