Skip to content

Commit 4141a78

Browse files
Problem 15 (#25)
* add initial template * add solution and resources * update readme
1 parent 6658b61 commit 4141a78

File tree

2 files changed

+126
-1
lines changed

2 files changed

+126
-1
lines changed

README.md

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@ As I work through this list I figure I would make a GitHub repo with my solution
3838
27. [01 Matrix #542](https://github.com/curtisbarnard/leetcode-grind75-javascript/blob/main/medium/01-matrix-542.md)
3939
28. [K Closest Points to Origin #973](https://github.com/curtisbarnard/leetcode-grind75-javascript/blob/main/medium/k-closest-origin-973.md)
4040
29. [Longest Substring Without Repeating Characters #3](https://github.com/curtisbarnard/leetcode-grind75-javascript/blob/main/medium/longest-substring-3.md)
41-
30. 3Sum #15
41+
30. [3Sum #15](https://github.com/curtisbarnard/leetcode-grind75-javascript/blob/main/medium/3sum-15.md)
4242
31. Binary Tree Level Order Traversal #102
4343
32. Clone Graph #133
4444
33. Evaluate Reverse Polish Notation #150
@@ -104,6 +104,7 @@ In order to practice with similar data structures I'll be placing each problem i
104104
- [K Closest Points to Origin #973](https://github.com/curtisbarnard/leetcode-grind75-javascript/blob/main/medium/k-closest-origin-973.md)
105105
- [Insert Interval #57](https://github.com/curtisbarnard/leetcode-grind75-javascript/blob/main/medium/insert-interval-57.md)
106106
- [01 Matrix #542](https://github.com/curtisbarnard/leetcode-grind75-javascript/blob/main/medium/01-matrix-542.md)
107+
- [3Sum #15](https://github.com/curtisbarnard/leetcode-grind75-javascript/blob/main/medium/3sum-15.md)
107108

108109
### Queue
109110

@@ -140,6 +141,7 @@ In order to practice with similar data structures I'll be placing each problem i
140141
- [Majority Element #169](https://github.com/curtisbarnard/leetcode-grind75-javascript/blob/main/easy/majority-element-169.md)
141142
- [Contains Duplicate #217](https://github.com/curtisbarnard/leetcode-grind75-javascript/blob/main/easy/contains-duplicate-217.md)
142143
- [Longest Substring Without Repeating Characters #3](https://github.com/curtisbarnard/leetcode-grind75-javascript/blob/main/medium/longest-substring-3.md)
144+
- [3Sum #15](https://github.com/curtisbarnard/leetcode-grind75-javascript/blob/main/medium/3sum-15.md)
143145

144146
### Binary Tree
145147

@@ -165,6 +167,7 @@ Within the problems above there are several patterns that often occur. I plan to
165167
- [Reverse Linked List #206](https://github.com/curtisbarnard/leetcode-grind75-javascript/blob/main/easy/reverse-linked-list-206.md)
166168
- [Middle of the Linked List #876](https://github.com/curtisbarnard/leetcode-grind75-javascript/blob/main/easy/middle-linked-list-876.md)
167169
- [Contains Duplicate #217](https://github.com/curtisbarnard/leetcode-grind75-javascript/blob/main/easy/contains-duplicate-217.md)
170+
- [3Sum #15](https://github.com/curtisbarnard/leetcode-grind75-javascript/blob/main/medium/3sum-15.md)
168171

169172
### Sliding Window
170173

medium/3Sum-15.md

Lines changed: 122 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,122 @@
1+
# 3Sum
2+
3+
Page on leetcode: https://leetcode.com/problems/3sum/
4+
5+
## Problem Statement
6+
7+
Given an integer array nums, return all the triplets [nums[i], nums[j], nums[k]] such that i != j, i != k, and j != k, and nums[i] + nums[j] + nums[k] == 0.
8+
9+
Notice that the solution set must not contain duplicate triplets.
10+
11+
### Constraints
12+
13+
- 3 <= nums.length <= 3000
14+
- -10<sup>5</sup> <= nums[i] <= 10<sup>5</sup>
15+
16+
### Example
17+
18+
```
19+
Input: nums = [-1,0,1,2,-1,-4]
20+
Output: [[-1,-1,2],[-1,0,1]]
21+
Explanation:
22+
nums[0] + nums[1] + nums[2] = (-1) + 0 + 1 = 0.
23+
nums[1] + nums[2] + nums[4] = 0 + 1 + (-1) = 0.
24+
nums[0] + nums[3] + nums[4] = (-1) + 2 + (-1) = 0.
25+
The distinct triplets are [-1,0,1] and [-1,-1,2].
26+
Notice that the order of the output and the order of the triplets does not matter.
27+
```
28+
29+
```
30+
Input: nums = [0,1,1]
31+
Output: []
32+
Explanation: The only possible triplet does not sum up to 0.
33+
```
34+
35+
```
36+
Input: nums = [0,0,0]
37+
Output: [[0,0,0]]
38+
Explanation: The only possible triplet sums up to 0.
39+
```
40+
41+
## Solution
42+
43+
- No duplicates of triplets (Can I exclude with a hashmap?)
44+
- Brute force possible with an O(n<sup>3</sup>) solution
45+
- Approach like two sum and store pairs as key's and remainder as values?
46+
- All possibilities is n<sup>3</sup> (aka a cube) Some of these are complimentary, how can we eliminate those so we don't have to calc twice?
47+
48+
### Pseudocode Attempt
49+
50+
1. Create map
51+
2. Create result
52+
3. Iterate thru nums with i
53+
4. Iterate thru nums with j = i + 1
54+
5. Store 0 - nums[i] - nums[j] in map with [nums[i], nums[j], false]
55+
6. If found add to result and change to true, if true don't add to result
56+
7. return result
57+
58+
### Initial Attempt
59+
60+
```javascript
61+
const threeSum = function (nums) {
62+
const map = {};
63+
const result = [];
64+
65+
for (let i = 0; i < nums.length; i++) {
66+
for (let j = i + 1; j < nums.length; j++) {
67+
const remainder = 0 - nums[i] - nums[j];
68+
if (remainder in map) {
69+
// Check if combo was already used
70+
if (!map[remainder][2]) {
71+
result.push([remainder, nums[i], nums[j]]);
72+
}
73+
} else {
74+
map[remainder] = [nums[i], nums[j], false];
75+
}
76+
}
77+
}
78+
79+
return result;
80+
};
81+
```
82+
83+
### Optimized Solution
84+
85+
The time complexity of below is O(n<sup>2</sup>) with a space complexity likely O(n) due to the sorting. https://www.youtube.com/watch?v=jzZsG8n2R9A
86+
87+
```javascript
88+
const threeSum = function (nums) {
89+
const result = [];
90+
nums.sort((a, b) => a - b);
91+
92+
for (let i = 0; i < nums.length; i++) {
93+
// This is an optimization as it exits iterating over the sorted array when num[i] becomes positive. Only positive numbers would be left in the array and you can't add them to make zero
94+
if (nums[i] > 0) {
95+
break;
96+
}
97+
98+
if (i > 0 && nums[i] === nums[i - 1]) {
99+
continue;
100+
}
101+
102+
let l = i + 1;
103+
let r = nums.length - 1;
104+
while (l < r) {
105+
const total = nums[i] + nums[l] + nums[r];
106+
if (total > 0) {
107+
r--;
108+
} else if (total < 0) {
109+
l++;
110+
} else {
111+
result.push([nums[i], nums[l], nums[r]]);
112+
l++;
113+
while (nums[l] === nums[l - 1] && l < r) {
114+
l++;
115+
}
116+
}
117+
}
118+
}
119+
120+
return result;
121+
};
122+
```

0 commit comments

Comments
 (0)