单调队列

单调队列,即队列内元素单调递增or递减的队列

如何维护?若当前元素大于队尾元素,则将队尾元素弹出,直至队列为空或当前元素小于队尾元素;若队首元素小于查询边界L,则弹出队首元素直至队首元素大于等于L

能用来干什么?给定长度为n的序列,在O(n)时间内得出每个长度为k的子区间的最大值or最小值

eg:

https://www.luogu.com.cn/problem/P2698

老板需要你帮忙浇花。给出N滴水的坐标,y表示水滴的高度,x表示它下落到x轴的位置。

每滴水以每秒1个单位长度的速度下落。你需要把花盆放在x轴上的某个位置,使得从被花盆接着的第1滴水开始,到被花盆接着的最后1滴水结束,之间的时间差至少为D。

我们认为,只要水滴落到x轴上,与花盆的边沿对齐,就认为被接住。给出N滴水的坐标和D的大小,请算出最小的花盆的宽度W。

即我们可以确定L,找到最小的R满足条件,遍历所有的L后取R-L最小值

将水滴按x排序后,我们可以维护两个队列来寻找最小值、最大值

先确定L=0,R=L,递增R并维护最小值与最大值直至满足条件

再使L++,此时弹出队首元素,易知此时R不可能比上一轮的值小,故R从上一轮的值开始递增并维护队列直至满足条件。

此时每个元素最多入一次队列,出一次队列,故时间复杂度为O(n)