在資料結構中,通常 stack 都會和 queue 被放在一起討論。
既然有單調棧(monotonic stack),那當然也有單調隊列(monotonic queue)。相對於單調棧,單調隊列的細節稍微多一點。單調隊列可以從兩端操作,因此像 python 會用 deque
的方式實現。
今天的範例題是 239. Sliding Window Maximum。這題也可以用滑動窗口(題目都告訴你了),不過我們姑且拿來練單調隊列。
首先當然是要維持一個隊列,這邊維持的是遞減的單調隊列。遇到比較小的數就 append 到最後,如果不是最小的,就一路 pop 直到符合性質為止。
假設目前的遞減隊列是 [a1, a2, a3, a4, a5],如果新元素 a2 < b1 < a3,由於 a3, a4, a5 都是在 b1 前面進列,這三個數一定會在 b1 出去前被 pop 掉,所以無論如何不可能成為 b1 進列後的最大值,因此就可以直接被刪掉。假設 b2 是最大值,那所有數字都可以直接被清空。
最後,隊列可以存 index 方便確認範圍,以上就是關於這題解法的所有細節了。
class Solution:
def maxSlidingWindow(self, nums: List[int], k: int) -> List[int]:
if not nums:
return []
max_values = [0]*(len(nums)-(k-1))
window = deque()
for i in range(len(nums)):
while window and window[0] < i - (k-1):
window.popleft()
while window and nums[i] >= nums[window[-1]]:
window.pop()
window.append(i)
if i >= k - 1:
max_values[i-(k-1)] = nums[window[0]]
return max_values