1+ class Solution (object ):
2+ #this is the answer from caikehe and all the comments below
3+
4+ """
5+ the main idea is to iterate every number in nums.
6+ we use the number as a target to find two other numbers which make total zero.
7+ for those two other numbers, we move pointers, l and r, to try them.
8+
9+ l start from left to right
10+ r start from right to left
11+
12+ first, we sort the array, so we can easily move i around and know how to adjust l and r.
13+ if the number is the same as the number before, we have used it as target already, continue. [1]
14+ we always start the left pointer from i+1 because the combination has already tried. [2]
15+
16+ now we calculate the total
17+ if the total is less than zero, we need it to be larger, so we move the left pointer. [3]
18+ if the total is greater than zero, we need it to be smaller, so we move the right pointer. [4]
19+ if the total is zero, bingo! [5]
20+ we need to move the left and right pointers to the next different numbers, so we do not get repeating result. [6]
21+
22+ we do not need to consider i after nums[i]>0, since sum of positive will be always greater than zero. [7]
23+ we do not need to try the last two, since there are no rooms for l and r pointers.
24+ You can think of it as The last two have been tried by all others. [8]
25+ """
26+
27+ def threeSum (self , nums ):
28+ res = []
29+ nums .sort ()
30+ length = len (nums )
31+ for i in xrange (length - 2 ): #[8]
32+ if nums [i ]> 0 : break #[7]
33+ if i > 0 and nums [i ]== nums [i - 1 ]: continue #[1]
34+
35+ l , r = i + 1 , length - 1 #[2]
36+ while l < r :
37+ total = nums [i ]+ nums [l ]+ nums [r ]
38+
39+ if total < 0 : #[3]
40+ l += 1
41+ elif total > 0 : #[4]
42+ r -= 1
43+ else : #[5]
44+ res .append ([nums [i ], nums [l ], nums [r ]])
45+ while l < r and nums [l ]== nums [l + 1 ]: #[6]
46+ l += 1
47+ while l < r and nums [r ]== nums [r - 1 ]: #[6]
48+ r -= 1
49+ l += 1
50+ r -= 1
51+ return res
52+
53+ """
54+ def threeSum(self, nums):
55+ def twoSum(target, nums):
56+ res = []
57+ seen = collections.Counter()
58+ for n1 in nums:
59+ n2 = target-n1
60+ if n1 in seen or n2 in seen or n2 not in nums: continue
61+ if n1==n2 and nums[n1]<2: continue
62+ seen[n1]+=1
63+ seen[n2]+=1
64+ res.append([target*-1, n1, n2])
65+ return res
66+
67+ res = []
68+ zero = 0
69+ positive = collections.Counter()
70+ negative = collections.Counter()
71+
72+ for n in nums:
73+ if n>0:
74+ positive[n]+=1
75+ elif n==0:
76+ zero+=1
77+ else:
78+ negative[n]+=1
79+
80+ if zero>=3:
81+ res.append([0, 0, 0])
82+ if zero>=1:
83+ for p in positive:
84+ if p*-1 in negative:
85+ res.append([0, p, p*-1])
86+
87+ for p in positive:
88+ res+=twoSum(p*-1, negative)
89+ for n in negative:
90+ res+=twoSum(n*-1, positive)
91+
92+ return res
93+ """
0 commit comments