题目
239. 滑动窗口最大值 - 力扣(LeetCode)
思路
使用一个队列充当不断滑动的窗口,每次滑动记录其中的最大值:
如何在 `O(1)` 时间计算最大值,只需要一个特殊的数据结构「单调队列」,`push` 方法依然在队尾添加元素,但是要把前面比自己小的元素都删掉,直到遇到更大的元素才停止删除。
代码
class Solution {/* 单调队列的实现 */class MonotonicQueue {LinkedList<Integer> q = new LinkedList<>();public void push(int n) {// 将小于 n 的元素全部删除while (!q.isEmpty() && q.getLast() < n) {q.pollLast();}// 然后将 n 加入尾部q.addLast(n);}public int max() {return q.getFirst();}public void pop(int n) {if (n == q.getFirst()) {q.pollFirst();}}}/* 解题函数的实现 */public int[] maxSlidingWindow(int[] nums, int k) {MonotonicQueue window = new MonotonicQueue();List<Integer> res = new ArrayList<>();for (int i = 0; i < nums.length; i++) {if (i < k - 1) {//先填满窗口的前 k - 1window.push(nums[i]);} else {// 窗口向前滑动,加入新数字window.push(nums[i]);// 记录当前窗口的最大值res.add(window.max());// 移出旧数字window.pop(nums[i - k + 1]);}}// 需要转成 int[] 数组再返回int[] arr = new int[res.size()];for (int i = 0; i < res.size(); i++) {arr[i] = res.get(i);}return arr;}
}