← DSADSA 1.1

Two Pointers

20 of 21 problems solved across all core sub-patterns — one problem (Partition Labels) circled back for later.

Two references walking across an array (or a linked list) instead of nesting loops — most of these collapse an O(n²) brute force down to O(n) just by moving two pointers with intent instead of comparing every pair.

The sub-patterns

  • A — Opposite Ends. Left starts at 0, right at the end, move inward based on a condition.
  • B — Opposite Ends + Sort. Sort first, then work inward from the ends — the whole k-Sum family lives here.
  • C — Same Direction. A slow (write) pointer and a fast (read) pointer both moving left to right.
  • D — Fast/Slow. One pointer at one step, one at two — cycles and midpoints on a linked list.
  • E — Partition (3-way). Dutch National Flag-style, splitting an array into three regions in one pass.
  • F — Sliding Window Hybrid. A variable-size window — expand the right edge, shrink the left.
  • G — Hash + Enumerate. Split the problem into two halves, hash one, enumerate the other.
Things that generalize across the whole pattern

Two things that generalize across almost every problem in this pattern: pointer movement should usually be unconditional — it's the update (tracking the best answer so far) that should be conditional, not the walk itself. And when skipping duplicates in a sorted array, checking ahead (nums[i] == nums[i+1]) and checking behind (nums[i] == nums[i-1]) both work — which one to use is a style choice about fixed vs. moving pointers, not a correctness issue.

Notes from readers

Comments — via GitHub