Lessons
Recommended Lessons
Two Pointers
Solve array/string problems in one pass by moving two indices instead of nesting loops.
Sliding Window
Scan contiguous subarrays/substrings by moving a window and updating your answer in O(1) per move.
Prefix Sum
Precompute cumulative totals so any range sum becomes a subtraction.
Hash Map
Use a hash map as fast memory: scan once, look up what you need in O(1) average time.
Binary Search
Repeatedly divide the search space in half to find a target value or boundary in O(log n) time.
Tree DFS
Traverse a tree by going as deep as possible along each branch before backtracking. Use recursion for elegant solutions.
Tree BFS
Traverse a tree level by level using a queue, processing all nodes at each depth before moving deeper.
Graph BFS
Explore a graph level by level, visiting all neighbors before moving deeper. Perfect for shortest path in unweighted graphs.
Graph DFS
Explore graphs by going as deep as possible along each path before backtracking. Use recursion or a stack.
Topological Sort
Order nodes in a directed graph so that for every edge u → v, node u comes before v. Essential for dependency resolution.
Union Find
Efficiently track and merge disjoint sets. Perfect for problems involving grouping, connectivity, or 'are these connected?' queries.
Bellman-Ford
Find shortest paths from a source in graphs with negative edge weights. Detect reachable negative cycles in O(V × E) time.
Bipartite Matching
Find the maximum number of pairings between two disjoint sets. Use augmenting paths to re-route when direct matches conflict.
DP 1D
Build solutions incrementally using a 1D array where each element depends on previous elements.
DP 2D
Build solutions using a 2D table where dp[i][j] represents the answer for a subproblem defined by two parameters.
DP Knapsack
Select items with weights and values to maximize value while staying within a capacity constraint. Foundation for many subset selection problems.
Backtracking
Systematically explore all possibilities by building candidates incrementally and abandoning ('backtracking') when a candidate cannot lead to a valid solution.
Monotonic Stack
A stack that maintains elements in sorted order (increasing or decreasing). Perfect for 'next greater/smaller element' problems.
Heap
A specialized tree structure that provides O(log n) insertion and O(1) access to the minimum or maximum element. Essential for 'top K' and priority-based problems.
Trie
A tree structure for efficient string prefix operations. Enables O(m) search, insert, and prefix queries where m is the string length.
Linked List
Manipulate nodes by rewiring pointers rather than shifting elements. Master traversal, reversal, and the fast/slow pointer trick.
Sorting: Basics (Insertion Sort)
Build a sorted array one element at a time by inserting each element into its correct position. O(n²) worst case, but O(n) on nearly-sorted data.
Sorting: Merge Sort
Divide the array in half, recursively sort each half, then merge the sorted halves. Always O(n log n) and stable.
Sorting: Counting Sort
Sort integers by counting occurrences instead of comparing. O(n + k) time, where k is the value range. This breaks the O(n log n) barrier for bounded integers.
String Matching (KMP)
Find patterns in text in O(n + m) time by precomputing where to resume after a mismatch. Never re-check characters you've already matched.