Sequences and Queries
What is this?
These are the trickiest, most satisfying uses of binary search โ the ones where you're not searching for a value you can see at all. You might be hunting the kth missing number, the dividing line between two sorted lists, or who was winning an election at some moment in time. The shared move is to invent a quantity that only ever grows as you move along, then binary-search the exact point where it crosses the target. A common companion trick is to do one slow pass up front to build a lookup, so that afterwards a flood of questions each get answered almost instantly.
๐ก Fun fact: The "do the heavy work once, then answer each question fast" idea here is the same one behind database indexes โ building the index is slow, but afterward millions of lookups fly, which is why a search that crawls without one can run thousands of times slower.
๐ The 5 problems in this chapter are free. Sign in with Google or Microsoft to start solving.
Core idea: Binary search can locate things that are not values at all โ a count of missing numbers, a partition point, the right moment in a timeline. The trick is to define a quantity that increases monotonically with the index (or the candidate), then binary-search the place where that quantity crosses your target. These are the hardest, most rewarding applications of the technique.
The pattern
Each problem here builds a monotonic signal and searches it. For "missing element" questions, the number of values missing before index i only grows as i grows, so you binary-search for where the missing-count reaches your target. The same gap-counting idea answers "the kth missing positive" by treating absent numbers as a running deficit.
A second idea is partition search: rather than merging two sorted arrays, binary-search the cut that splits the combined elements into a correct left and right half โ that is how the median falls out in log time without ever merging.
A third idea is precompute, then query: do one linear pass to build a structure (a leader-over-time timeline, prefix counts of an item), then answer each query with a binary search or an array lookup. The work moves from per-query to one-time setup.
The problems
Missing Element in Sorted Array โ find the kth missing value. Count missing before index: at index i, missing-so-far is nums[i] โ nums[0] โ i; binary-search the first index where that count reaches k, then offset into the gap.
Kth Missing Positive Number โ find the kth absent positive integer. Same gap counting: at index i, the missing count is nums[i] โ (i + 1); binary-search where it first reaches k.
Median of Two Sorted Arrays โ the classic O(log(min(m, n))) problem. Partition search: binary-search a cut in the smaller array that, paired with the complementary cut in the larger, puts the right counts on each side and satisfies the order condition โ the median sits at the boundary.
Online Election โ answer "who led at time t?" repeatedly. Precompute leaders in one pass over the votes, store the time of each lead change, then bisect time to find the leader for each query in O(log n).
Plates Between Candles โ count plates strictly between two candles for many queries. Build prefix counts of plates and, for each query, find the nearest candle inward on each side (precomputed or via binary search), then subtract prefix counts.
Key takeaways
- Search a monotonic quantity, not the raw array. Missing-counts, partitions, and lead-times all grow predictably โ binary-search the crossing point.
- Gap counting answers "missing" questions. A simple formula at each index turns absence into a searchable count.
- Partition instead of merge. The median comes from finding the right split, never from combining the arrays.
- Precompute once, query many. Build a timeline or prefix array up front so each query is O(log n) or O(1).
- Why this chapter matters: it stretches binary search to its limits, the level expected for hard interview rounds and the foundation for query-heavy problems.
Online Election
Core idea: The leader only changes at vote moments, so precompute the winner on every interval once, then answer any "who was leading at time T?" query with a single binary search.
Problem, rephrased
You're running the live scoreboard for a televised talent show. Viewers phone in votes for contestants over the course of the night. Each call is logged as a pair: which contestant got the vote, and the timestamp it arrived. The timestamps are strictly increasing โ calls are processed one at a time, no two share a clock tick.
The producers keep yelling things like "Who was winning at 9:42?" โ sometimes about a moment between calls, sometimes exactly when a call landed. You must answer instantly, possibly hundreds of times.
Two rules nail down "winning":
- A vote that arrives at exactly the queried time counts toward that query.
- On a tie in vote totals, the contestant who reached that total most recently wins.
You build the class once, then field many queries:
TopVotedCandidate(persons, times) # one-time setup
.q(t) # who led at time t?
Take persons = [0, 1, 1, 0, 0, 1, 0] and times = [0, 5, 10, 15, 20, 25, 30].
| Call | Time t |
Votes counted (at or before t) |
Tallies | Leader | Why |
|---|---|---|---|---|---|
q(3) |
3 | [0] |
0:1 | 0 | only one vote so far |
q(12) |
12 | [0,1,1] |
0:1, 1:2 | 1 | contestant 1 pulls ahead |
q(25) |
25 | [0,1,1,0,0,1] |
0:3, 1:3 | 1 | tie 3โ3, but 1 reached 3 more recently |
q(15) |
15 | [0,1,1,0] |
0:2, 1:2 | 0 | tie 2โ2, 0's vote at t=15 is most recent |
q(24) |
24 | [0,1,1,0,0] |
0:3, 1:2 | 0 | 0 is now clearly ahead |
q(8) |
8 | [0,1] |
0:1, 1:1 | 1 | tie 1โ1, 1's vote at t=5 is most recent |
Output: [0, 1, 1, 0, 0, 1] โ and notice how the tie-by-recency rule does real work in q(25), q(15), and q(8).
Sign in to continue reading
The rest of this lesson is available with a free account. Signing in with Google or Microsoft is free.
Sign in to read the full lesson