mirror of
https://github.com/Rainyy21/framework_note.git
synced 2026-10-10 23:40:30 -04:00
376 lines
16 KiB
Markdown
376 lines
16 KiB
Markdown
---
|
|
tags:
|
|
- leetcode/array-hashing
|
|
- study-guide
|
|
- coding-practice
|
|
difficulty_distribution:
|
|
easy: 7
|
|
medium: 10
|
|
hard: 3
|
|
total_problems: 20
|
|
completed_problems: 1
|
|
progress_percentage: 5%
|
|
last_updated: 2026-05-26
|
|
---
|
|
|
|
# 🚀 Array & Hashing: LeetCode Master List
|
|
|
|
Welcome to your study guide for **Array and Hashing**! This topic is the bedrock of coding interviews, establishing the core patterns for lookups, frequency counting, prefix arrays, and space-time tradeoffs.
|
|
|
|
---
|
|
|
|
## 📊 Progress Tracker
|
|
|
|
| Status | # | Problem | Difficulty | Key Technique | Links |
|
|
| :----: | :--: | :------------------------------------------------------------------------------------------------------------------------ | :--------: | :----------------------------- | :--------------------------------------------------------------------------------------: |
|
|
| [x] | 1 | [Two Sum](https://leetcode.com/problems/two-sum/) | 🟢 Easy | Hash Map Complement | [LeetCode](https://leetcode.com/problems/two-sum/) |
|
|
| [ ] | 217 | [Contains Duplicate](https://leetcode.com/problems/contains-duplicate/) | 🟢 Easy | Hash Set Presence | [LeetCode](https://leetcode.com/problems/contains-duplicate/) |
|
|
| [ ] | 242 | [Valid Anagram](https://leetcode.com/problems/valid-anagram/) | 🟢 Easy | Frequency Count / Sorting | [LeetCode](https://leetcode.com/problems/valid-anagram/) |
|
|
| [ ] | 169 | [Majority Element](https://leetcode.com/problems/majority-element/) | 🟢 Easy | Boyer-Moore Voting / Hash Map | [LeetCode](https://leetcode.com/problems/majority-element/) |
|
|
| [ ] | 290 | [Word Pattern](https://leetcode.com/problems/word-pattern/) | 🟢 Easy | Bijective Hash Mapping | [LeetCode](https://leetcode.com/problems/word-pattern/) |
|
|
| [ ] | 1346 | [Check If N and Its Double Exist](https://leetcode.com/problems/check-if-n-and-its-double-exist/) | 🟢 Easy | Hash Set Double-Lookup | [LeetCode](https://leetcode.com/problems/check-if-n-and-its-double-exist/) |
|
|
| [ ] | 724 | [Find Pivot Index](https://leetcode.com/problems/find-pivot-index/) | 🟢 Easy | Prefix Sum Balance | [LeetCode](https://leetcode.com/problems/find-pivot-index/) |
|
|
| [ ] | 49 | [Group Anagrams](https://leetcode.com/problems/group-anagrams/) | 🟡 Medium | Categorization Key Mapping | [LeetCode](https://leetcode.com/problems/group-anagrams/) |
|
|
| [ ] | 347 | [Top K Frequent Elements](https://leetcode.com/problems/top-k-frequent-elements/) | 🟡 Medium | Bucket Sort / Heap Tracking | [LeetCode](https://leetcode.com/problems/top-k-frequent-elements/) |
|
|
| [ ] | 238 | [Product of Array Except Self](https://leetcode.com/problems/product-of-array-except-self/) | 🟡 Medium | Left/Right Prefix Products | [LeetCode](https://leetcode.com/problems/product-of-array-except-self/) |
|
|
| [ ] | 36 | [Valid Sudoku](https://leetcode.com/problems/valid-sudoku/) | 🟡 Medium | Sub-grid Hashing (Bitmask/Set) | [LeetCode](https://leetcode.com/problems/valid-sudoku/) |
|
|
| [ ] | 128 | [Longest Consecutive Sequence](https://leetcode.com/problems/longest-consecutive-sequence/) | 🟡 Medium | Hash Set Boundary Scan | [LeetCode](https://leetcode.com/problems/longest-consecutive-sequence/) |
|
|
| [ ] | 560 | [Subarray Sum Equals K](https://leetcode.com/problems/subarray-sum-equals-k/) | 🟡 Medium | Prefix Sum + Frequency Map | [LeetCode](https://leetcode.com/problems/subarray-sum-equals-k/) |
|
|
| [ ] | 271 | [Encode and Decode Strings](https://leetcode.com/problems/encode-and-decode-strings/) | 🟡 Medium | Length-Prefix Chunking | [LeetCode](https://leetcode.com/problems/encode-and-decode-strings/) |
|
|
| [ ] | 442 | [Find All Duplicates in an Array](https://leetcode.com/problems/find-all-duplicates-in-an-array/) | 🟡 Medium | In-place Sign Negation | [LeetCode](https://leetcode.com/problems/find-all-duplicates-in-an-array/) |
|
|
| [ ] | 380 | [Insert Delete GetRandom O(1)](https://leetcode.com/problems/insert-delete-getrandom-o1/) | 🟡 Medium | Array + Map Index Swapping | [LeetCode](https://leetcode.com/problems/insert-delete-getrandom-o1/) |
|
|
| [ ] | 2017 | [Grid Game](https://leetcode.com/problems/grid-game/) | 🟡 Medium | 2-Row Prefix Sum Selection | [LeetCode](https://leetcode.com/problems/grid-game/) |
|
|
| [ ] | 41 | [First Missing Positive](https://leetcode.com/problems/first-missing-positive/) | 🔴 Hard | Cyclic In-place Sorting | [LeetCode](https://leetcode.com/problems/first-missing-positive/) |
|
|
| [ ] | 30 | [Substring with Concatenation](https://leetcode.com/problems/substring-with-concatenation-of-all-words/) | 🔴 Hard | Sliding Window + Count Maps | [LeetCode](https://leetcode.com/problems/substring-with-concatenation-of-all-words/) |
|
|
| [ ] | 381 | [Insert Delete GetRandom O(1) - Duplicates](https://leetcode.com/problems/insert-delete-getrandom-o1-duplicates-allowed/) | 🔴 Hard | Array + Map to Set of Indices | [LeetCode](https://leetcode.com/problems/insert-delete-getrandom-o1-duplicates-allowed/) |
|
|
|
|
---
|
|
|
|
## 🟢 Easy Problems (7)
|
|
|
|
### 1. Two Sum (LC 1)
|
|
> [!TIP]
|
|
> **Core Concept:** Instead of checking all pairs, store the numbers you have seen in a hash map mapping `value -> index`. For each `num`, check if its complement (`target - num`) is already in the map.
|
|
|
|
- **Complexity Target:** $O(n)$ Time | $O(n)$ Space
|
|
- **Starter Template:**
|
|
```python
|
|
def twoSum(nums: list[int], target: int) -> list[int]:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
### 2. Contains Duplicate (LC 217)
|
|
> [!TIP]
|
|
> **Core Concept:** Iterate through the array and store each element in a Hash Set. If the element is already in the set, a duplicate has been found.
|
|
|
|
- **Complexity Target:** $O(n)$ Time | $O(n)$ Space
|
|
- **Starter Template:**
|
|
```python
|
|
def containsDuplicate(nums: list[int]) -> bool:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
### 3. Valid Anagram (LC 242)
|
|
> [!TIP]
|
|
> **Core Concept:** Count the frequency of characters in both strings. You can use two hash maps, or a single array size 26 if constraints are purely lowercase a-z. Compare the frequency distributions.
|
|
|
|
- **Complexity Target:** $O(n)$ Time | $O(1)$ Space (since lowercase English alphabet count is fixed at 26)
|
|
- **Starter Template:**
|
|
```python
|
|
def isAnagram(s: str, t: str) -> bool:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
### 4. Majority Element (LC 169)
|
|
> [!TIP]
|
|
> **Core Concept:** While a Hash Map works, you can solve this in $O(1)$ space using **Boyer-Moore Voting Algorithm**. Keep a `candidate` and a `count`. When `count == 0`, pick the current element as candidate. Increment `count` if the element matches the candidate, else decrement it.
|
|
|
|
- **Complexity Target:** $O(n)$ Time | $O(1)$ Space
|
|
- **Starter Template:**
|
|
```python
|
|
def majorityElement(nums: list[int]) -> int:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
### 5. Word Pattern (LC 290)
|
|
> [!TIP]
|
|
> **Core Concept:** Establish a bijective (two-way) mapping between character in `pattern` and words in string `s` using two hash maps. If a key maps to a different value in either map, return `False`.
|
|
|
|
- **Complexity Target:** $O(n)$ Time | $O(n)$ Space (where $n$ is total chars/words)
|
|
- **Starter Template:**
|
|
```python
|
|
def wordPattern(pattern: str, s: str) -> bool:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
### 6. Check If N and Its Double Exist (LC 1346)
|
|
> [!TIP]
|
|
> **Core Concept:** Iterate through the array. Check if `2 * num` or `num / 2` (if divisible by 2) exists in your Hash Set of previously visited values.
|
|
|
|
- **Complexity Target:** $O(n)$ Time | $O(n)$ Space
|
|
- **Starter Template:**
|
|
```python
|
|
def checkIfExist(arr: list[int]) -> bool:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
### 7. Find Pivot Index (LC 724)
|
|
> [!TIP]
|
|
> **Core Concept:** Compute the total sum of the array. Track the running `left_sum`. For each index, check if `left_sum == total_sum - left_sum - num`. If it is, that's the pivot.
|
|
|
|
- **Complexity Target:** $O(n)$ Time | $O(1)$ Space
|
|
- **Starter Template:**
|
|
```python
|
|
def pivotIndex(nums: list[int]) -> int:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
## 🟡 Medium Problems (10)
|
|
|
|
### 8. Group Anagrams (LC 49)
|
|
> [!TIP]
|
|
> **Core Concept:** Group words by their character signature. The signature can be a sorted string, or a character count tuple `[0] * 26` mapped to list of matching strings.
|
|
|
|
- **Complexity Target:** $O(n \cdot m)$ Time (where $m$ is max word length) | $O(n \cdot m)$ Space
|
|
- **Starter Template:**
|
|
```python
|
|
def groupAnagrams(strs: list[str]) -> list[list[str]]:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
### 9. Top K Frequent Elements (LC 347)
|
|
> [!TIP]
|
|
> **Core Concept:** Count frequencies using a hash map. Instead of sorting (which is $O(n \log n)$), use **Bucket Sort** where index represents frequencies. Since the max frequency is capped at `len(nums)`, we can assemble the result in linear time.
|
|
|
|
- **Complexity Target:** $O(n)$ Time | $O(n)$ Space
|
|
- **Starter Template:**
|
|
```python
|
|
def topKFrequent(nums: list[int], k: int) -> list[int]:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
### 10. Product of Array Except Self (LC 238)
|
|
> [!TIP]
|
|
> **Core Concept:** Create an output array. Do a forward pass to store the prefix product at each index. Then do a backward pass, keeping a running suffix product, multiplying it into your result.
|
|
|
|
- **Complexity Target:** $O(n)$ Time | $O(1)$ Extra Space (excluding output array)
|
|
- **Starter Template:**
|
|
```python
|
|
def productExceptSelf(nums: list[int]) -> list[int]:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
### 11. Valid Sudoku (LC 36)
|
|
> [!TIP]
|
|
> **Core Concept:** Track duplicates in rows, columns, and 3x3 sub-grids. Use a set for each row, column, and sub-grid. The subgrid index can be identified using `(r // 3, c // 3)`.
|
|
|
|
- **Complexity Target:** $O(1)$ Time & Space (since grid size is constant $9 \times 9$)
|
|
- **Starter Template:**
|
|
```python
|
|
def isValidSudoku(board: list[list[str]]) -> bool:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
### 12. Longest Consecutive Sequence (LC 128)
|
|
> [!TIP]
|
|
> **Core Concept:** Convert the array to a Hash Set. Loop through each number; if `num - 1` is not in the set, it means `num` is the *start* of a new sequence. Scan forward (`num + 1`, `num + 2`...) to find the sequence length. This guarantees each element is processed at most twice.
|
|
|
|
- **Complexity Target:** $O(n)$ Time | $O(n)$ Space
|
|
- **Starter Template:**
|
|
```python
|
|
def longestConsecutive(nums: list[int]) -> int:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
### 13. Subarray Sum Equals K (LC 560)
|
|
> [!TIP]
|
|
> **Core Concept:** Use prefix sum properties. If the difference between current prefix sum and target `k` (i.e. `prefix_sum - k`) was seen previously as a prefix sum, the subarray between those indices sums to `k`. Store prefix sum frequencies in a map.
|
|
|
|
- **Complexity Target:** $O(n)$ Time | $O(n)$ Space
|
|
- **Starter Template:**
|
|
```python
|
|
def subarraySum(nums: list[int], k: int) -> int:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
### 14. Encode and Decode Strings (LC 271 / Premium)
|
|
> [!TIP]
|
|
> **Core Concept:** To combine strings safely, prepend each string with its length followed by a delimiter (e.g. `"4#neet"`). When decoding, parse the number, jump past the delimiter, and slice that exact length.
|
|
|
|
- **Complexity Target:** $O(n)$ Time | $O(1)$ Extra Space (excluding output list)
|
|
- **Starter Template:**
|
|
```python
|
|
class Codec:
|
|
def encode(self, strs: list[str]) -> str:
|
|
pass
|
|
|
|
def decode(self, s: str) -> list[str]:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
### 15. Find All Duplicates in an Array (LC 442)
|
|
> [!TIP]
|
|
> **Core Concept:** The array contains elements from `1` to `n`. You can use the values as indices. As you iterate, look up `nums[abs(x) - 1]`. If it is positive, negate it. If it is already negative, then `abs(x)` has been seen before.
|
|
|
|
- **Complexity Target:** $O(n)$ Time | $O(1)$ Extra Space
|
|
- **Starter Template:**
|
|
```python
|
|
def findDuplicates(nums: list[int]) -> list[int]:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
### 16. Insert Delete GetRandom O(1) (LC 380)
|
|
> [!TIP]
|
|
> **Core Concept:** Store values in an Array List to achieve $O(1)$ random lookups. Maintain a Hash Map `val -> index` to achieve $O(1)$ insertions and updates. When deleting, swap the element to delete with the last element in the array, update the map, and pop from the array.
|
|
|
|
- **Complexity Target:** $O(1)$ Time average | $O(n)$ Space
|
|
- **Starter Template:**
|
|
```python
|
|
class RandomizedSet:
|
|
def __init__(self):
|
|
pass
|
|
|
|
def insert(self, val: int) -> bool:
|
|
pass
|
|
|
|
def remove(self, val: int) -> bool:
|
|
pass
|
|
|
|
def getRandom(self) -> int:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
### 17. Grid Game (LC 2017)
|
|
> [!TIP]
|
|
> **Core Concept:** The first robot splits the grid into two paths. Compute prefix sums for row 0 and row 1. Robot 1 wants to minimize Robot 2's maximum score, which will always be the max of the remaining top-right elements or bottom-left elements after Robot 1 pivots.
|
|
|
|
- **Complexity Target:** $O(n)$ Time | $O(n)$ Space (or $O(1)$ if prefix sums are computed on-the-fly)
|
|
- **Starter Template:**
|
|
```python
|
|
def gridGame(grid: list[list[int]]) -> int:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
## 🔴 Hard Problems (3)
|
|
|
|
### 18. First Missing Positive (LC 41)
|
|
> [!TIP]
|
|
> **Core Concept:** Use **Cyclic Sort** style placement. Iterate through the array and try to place each number `x` (if it lies in range `[1, n]`) at its correct index `x - 1`. Perform this swap in a loop. Finally, scan the array to find the first index `i` where `nums[i] != i + 1`.
|
|
|
|
- **Complexity Target:** $O(n)$ Time | $O(1)$ Space
|
|
- **Starter Template:**
|
|
```python
|
|
def firstMissingPositive(nums: list[int]) -> int:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
### 19. Substring with Concatenation of All Words (LC 30)
|
|
> [!TIP]
|
|
> **Core Concept:** All words are of equal length `L`. Use a sliding window starting at each offset `0 <= i < L`. For each window, use a hash map to count occurrences of words of length `L` and compare it with the count map of the target `words` list.
|
|
|
|
- **Complexity Target:** $O(n \cdot L)$ Time (where $n$ is string length, $L$ is word length) | $O(m \cdot L)$ Space (where $m$ is number of words)
|
|
- **Starter Template:**
|
|
```python
|
|
def findSubstring(s: str, words: list[str]) -> list[int]:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|
|
|
|
---
|
|
|
|
### 20. Insert Delete GetRandom O(1) - Duplicates Allowed (LC 381)
|
|
> [!TIP]
|
|
> **Core Concept:** Similar to LC 380, but the Hash Map now maps `val -> Set of indices` where the value resides in our dynamic list. During deletion, lookup any index from the value's set, swap with the list's last element, and update the set of the swapped element accordingly.
|
|
|
|
- **Complexity Target:** $O(1)$ Time average | $O(n)$ Space
|
|
- **Starter Template:**
|
|
```python
|
|
class RandomizedCollection:
|
|
def __init__(self):
|
|
pass
|
|
|
|
def insert(self, val: int) -> bool:
|
|
pass
|
|
|
|
def remove(self, val: int) -> bool:
|
|
pass
|
|
|
|
def getRandom(self) -> int:
|
|
pass
|
|
```
|
|
- **My Notes / Solution:**
|
|
*
|