題目描述:空中有一些氣球,每個氣球用水平範圍 [xstart, xend] 表示。可以從 x 軸上任意一點垂直向上射出一支箭,只要箭的 x 座標落在 xstart <= x <= xend 的範圍內,該氣球就會被戳破。問最少需要幾支箭才能戳破所有氣球?
解題思路:這是經典的貪心區間問題。關鍵洞察:若依照結束座標排序後,對第一個氣球在其結尾處射一箭,這是最能「覆蓋最多後續氣球」的選擇。排序後,從左到右掃描:以第一支箭射在第一個氣球的右端(arrow = points[0][1])。接著,若下一個氣球的起始點 xstart > arrow,代表現有箭無法覆蓋它,必須新增一支箭並更新箭的位置為該氣球的右端。如此重複直到掃描完所有氣球,箭的總數即為答案。
時間複雜度:O(n log n) — 瓶頸在於對氣球陣列依結束座標排序,後續的線性掃描為 O(n),整體由排序步驟決定。
空間複雜度:O(1) — 排序在原地進行(或使用 O(log n) 的遞迴排序棧),掃描過程只需常數個額外變數。
1. If points is empty, return 0.
2. Sort points by their end coordinate (ascending).
3. Initialize arrows = 1, arrowPos = points[0][1].
4. For each balloon i from 1 to n-1:
a. If points[i][0] > arrowPos (balloon starts after current arrow):
- Increment arrows.
- Set arrowPos = points[i][1].
5. Return arrows.方法一:依起始座標排序(Sort by Start) 改以起始座標排序,並維護當前箭可覆蓋的最右邊界。每遇到新氣球就更新覆蓋右界的最小值(取交集);若新氣球的起始點超出現有覆蓋範圍,則射出新箭。邏輯上與依結束座標排序等效,但程式需額外維護「當前箭的覆蓋上限」。時間複雜度 O(n log n),空間複雜度 O(1)。
方法二:區間覆蓋轉化(Interval Cover Reduction) 將問題轉化為「最少不重疊區間數量」(LeetCode 435 Non-overlapping Intervals 的變形)。每組不重疊的氣球需要獨立一支箭。思路相同,但從「最大不重疊區間組數」的角度出發,可以更清楚地看出本題與 435 題的關聯。時間複雜度 O(n log n),空間複雜度 O(1)。