An interactive visualization of the two-pointer approach to finding all intersections between two sorted interval lists. Watch how the algorithm compares intervals and advances pointers to collect every overlap.
Intervals LeetCode 986 โ MediumfirstList and secondList, where
firstList[i] = [start_i, end_i] and secondList[j] = [start_j, end_j].
Each list of intervals is pairwise disjoint and in sorted order.[a, b]
(with a <= b) denotes the set of real numbers x with a <= x <= b.[1, 3] and [2, 4] is [2, 3].
fun intervalIntersection(firstList: Array<IntArray>, secondList: Array<IntArray>): List<IntArray> { val result = mutableListOf<IntArray>() var i = 0; var j = 0 while (i < firstList.size && j < secondList.size) { val lo = maxOf(firstList[i][0], secondList[j][0]) val hi = minOf(firstList[i][1], secondList[j][1]) if (lo <= hi) result.add(intArrayOf(lo, hi)) if (firstList[i][1] < secondList[j][1]) i++ else j++ } return result}
Since both interval lists are already sorted and pairwise disjoint, we can use two pointers to
efficiently find all intersections in a single pass. At each step, we compare the current interval from each list.
The intersection of two intervals [a1, a2] and [b1, b2] is [max(a1, b1), min(a2, b2)],
and it exists only when max(a1, b1) <= min(a2, b2).
i = 0 and j = 0 for the two lists, and an empty result list.lo = max(A[i][0], B[j][0]), hi = min(A[i][1], B[j][1]).lo <= hi, this is a valid intersection โ add [lo, hi] to the result.A[i][1] < B[j][1], increment i; otherwise increment j.The interval that ends first cannot possibly intersect with any later interval from the other list (since both lists are sorted). So we can safely move past it. The interval that ends later, however, might still overlap with the next interval from the other list, so we keep it.
Each pointer moves forward at most m or n times respectively, where m and n
are the lengths of the two lists. Each step does constant work. The output can contain at most m + n intervals
in the worst case, so space is O(m + n) for the result.