Top 5 DSA Patterns I Used to Crack LeetCode Challenges
After solving 1000+ problems on LeetCode and CodeForces and reaching a max rating of 1810 on Leetcode, I noticed that most problems fall into repeatable patterns. Here are the 5 that helped me the most.
🔥 Why Patterns Matter
When I started DSA, I used to solve problems randomly. But things changed when I began spotting repeatable problem patterns. Once you master a pattern, you can apply it to dozens of problems — it’s like unlocking a cheat code in LeetCode.
🔁 1. Sliding Window
This pattern is a game-changer for problems involving subarrays, strings, or windows of size k
.
When to Use: You need to find max/min/average in a window, or the longest/shortest substring with some condition.
// LeetCode 3: Longest Substring Without Repeating Characters
int lengthOfLongestSubstring(string s) {
unordered_set<char> seen;
int left = 0, right = 0, maxLen = 0;
while (right < s.length()) {
if (seen.find(s[right]) == seen.end()) {
seen.insert(s[right++]);
maxLen = max(maxLen, right - left);
} else {
seen.erase(s[left++]);
}
}
return maxLen;
}
📊 2. Prefix Sum / Difference Array
Prefix sum is my go-to for range sum queries or subarray comparisons.
Example Problems:
- Range Sum Query (LeetCode 303)
- Subarray Sum Equals K (LeetCode 560)
// LeetCode 560: Subarray Sum Equals K
int subarraySum(vector<int>& nums, int k) {
unordered_map<int, int> prefix;
prefix[0] = 1;
int sum = 0, count = 0;
for (int num : nums) {
sum += num;
if (prefix.count(sum - k)) count += prefix[sum - k];
prefix[sum]++;
}
return count;
}
🔄 3. Two Pointers
Two pointers are great for sorted arrays or problems involving distances, duplicates, or merging.
Where I Used It: Merge intervals, remove duplicates, 3Sum, container with most water.
// LeetCode 167: Two Sum II - Input Array Is Sorted
int twoSum(vector<int>& nums, int target) {
int left = 0, right = nums.size() - 1;
while (left < right) {
int sum = nums[left] + nums[right];
if (sum == target) return {left + 1, right + 1};
else if (sum < target) left++;
else right--;
}
return {};
}
🧠 4. Binary Search (Classic + Variations)
This isn’t just for searching in arrays. I used binary search for finding answers in range-based problems or minimizing/maximizing functions.
Example Applications:
- Search in Rotated Sorted Array
- Koko Eating Bananas (Search on answer)
- Median of Two Sorted Arrays
🌳 5. DFS + Backtracking
Used heavily in recursion-based problems: permutations, subsets, N-Queens, Sudoku Solver, etc.
// LeetCode 46: Permutations
void backtrack(vector<int>& nums, vector<bool>& used, vector<int>& path, vector<vector<int>>& res) {
if (path.size() == nums.size()) {
res.push_back(path);
return;
}
for (int i = 0; i < nums.size(); ++i) {
if (used[i]) continue;
used[i] = true;
path.push_back(nums[i]);
backtrack(nums, used, path, res);
path.pop_back();
used[i] = false;
}
}
vector<vector<int>> permute(vector<int>& nums) {
vector<vector<int>> res;
vector<int> path;
vector<bool> used(nums.size(), false);
backtrack(nums, used, path, res);
return res;
}
📚 Final Thoughts
Once I recognized patterns in LeetCode problems, I stopped feeling stuck. I wasn’t guessing — I was mapping problems to strategies I already understood.
My tip: Don’t just solve problems. Group them by patterns, master those patterns, and apply them like tools in a toolkit.
💻 My LeetCode: leetcode.com/u/rhythm_21
👨💻 GitHub: github.com/rhythm217
📲 Connect: LinkedIn
Short and concised... great work
ReplyDelete