Shubham Sourabhthe room · director's cutplain résumé
Room 04 · The Grind — Intervals

Non Overlapping Intervals

MEDIUM✓ CHIP-TIMEDLC #435 — FULL STATEMENT

The briefingthe full drill, in my own words

The drill: A set of intervals has some pairwise overlaps. Remove the fewest possible so that what remains never overlaps — touching at a shared endpoint is fine.

A collection of intervals, each described by a start and an end, sits together on one line — and some of them cross each other in time. The task is to strip away as few of them as possible so that whatever remains never overlaps.

Two intervals overlap only when one genuinely begins before the other ends; sharing a single endpoint, where one interval ends exactly where the next begins, counts as clean and never forces a removal.

The number handed back is just a count — how many intervals had to go — not the intervals themselves. The input list's own order carries no meaning; only the raw start and end pairs matter.

  • dozens to low thousands of intervals in a single call
  • start and end values can be any integers, including negative ones
  • an interval's end is never before its own start
  • touching endpoints (one end equal to the next start) never count as overlap
EX 01
intervals = [[1, 3], [3, 6], [2, 4]]
→ 1
one overlap in a chain of three
EX 02
intervals = [[1, 2], [3, 4], [5, 6]]
→ 0
already non-overlapping
EX 03
intervals = [[1, 4], [1, 4], [1, 4]]
→ 2
three identical intervals, keep one

The hintstake only what you need

HINT 1 THE NUDGE

Removing intervals to kill overlaps is really about choosing which ones to KEEP — and the ones kept should leave as much room as possible for the rest. What quantity, sorted first, maximizes remaining room?

HINT 2 THE STRUCTURE

Sort by end time. The interval that finishes earliest always leaves the most room for whatever comes after it, so it is never wrong to keep it.

HINT 3 ONE STEP FROM THE ANSWER

Greedily keep the earliest-ending interval that still starts at or after the last kept interval's end; every interval that starts before that is an overlap you must discard — count those discards.

Coach's boardthe pattern, step by step

GREEDY BY END TIMEPATTERN · GREEDY — SORT BY ENDintervals = [[1,3],[3,6],[2,4]]
[1,3]
[2,4]
[3,6]
PREV END / REMOVED
prev_end → –
removed → 0
STEP 1

Sort by end time: [1,3], [2,4], [3,6]. Keep whichever interval finishes earliest — it always leaves the most room.

STEP 1 / 7 · ← → WORK TOO

The splitstwo paces, two languages

grind/non-overlapping-intervals.py — RACE PACE
LANG ▸
PACE ▸
class Solution:
    def eraseOverlapIntervals(self, intervals: List[List[int]]) -> int:
        if not intervals:
            return 0
        ivs = sorted(intervals, key=lambda iv: iv[1])
        removed = 0
        prev_end = ivs[0][1]
        for start, end in ivs[1:]:
            if start < prev_end:
                removed += 1
            else:
                prev_end = end
        return removed
TIME O(N LOG N)SPACE O(1)PYTHON · RACE PACE · 13 LN

✓ CHIP-TIMEDALL 4 SOLUTIONS RAN GREEN AGAINST SELF-AUTHORED CASES IN CI · JDK 21 · CPYTHON 3.12 · NOTHING PUBLISHES RED