單調佇列小記 滑動視窗

2022-04-12 03:02:00 字數 1888 閱讀 9292

一些廢話:

紀念hin久以前gellygoat大佬給我們講了以後窩就再也沒動過的單調佇列

qbxt的電腦編譯一次9s+可海星

f10真好用

題目傳送

資料看起來能用線段樹卡過?

這道題作為單調佇列的板子題當然是用單調佇列了

這裡呢,我們設兩個單調佇列(dalao是用乙個,但我不是dalao,只會用兩個)

既然是單調佇列,佇列裡面的元素肯定是單調的。但是注意單調佇列不是優先佇列

單調佇列其實是乙個雙端佇列

先貼一下雙端佇列常用的函式

插入:從隊頭插入:q.push_front();

從隊尾插入:q.push_back();

雙端佇列的某一元素前插入乙個元素x:iterator insert(iterator it,const t& x)

雙端佇列中某一元素前增加n個相同的元素x:void insert(iterator it,int n,const t& x)

刪除:刪除隊頭的元素:q.pop_front()

刪除隊尾的元素:q.pop_back()

清空佇列:q.clear()

刪除某一元素:iterator erase(iterator it)

更多用法見這裡

拿維護最小值的那個佇列舉例好了

我們維護隊頭是當前區間的最小值。

如果當前佇列的第乙個數的下標小於now(當前滑塊的左端點),就說明它該退役了,pop掉(注意佇列要非空)

我們從隊尾插入新的數。如果隊尾當前的數比a[x](要插入的數)大,此時隊尾的數的下標一定比x小,也就比a[x]更早失去效果。由此看來,當前隊尾的數不可能成為最小的數的候選者,所以我們把它pop掉

經過上面兩輪pop,就可以將a[x]放到隊尾了

細節什麼的見**吧

#include#include

#include

#include

#include

#include

#include

#include

#include

#include

using

namespace

std;

inline

intread()

while(ch>='

0'&&ch<='9'

)

return f?-x:x;

}int now,n,k,a[1000009],mi[1000009],ma[1000009

],cnt;

struct

dl//

建構函式

};deque

qma,qmi;//

qma維護最大值,qmi維護最小值

void pshmax(int

x)void pshmin(int

x)void

luangao()

}int

main()

ma[1]=qma.front().zhi;

mi[1]=qmi.front().zhi;

cnt=1

; luangao();

for(int i=1;i<=cnt;i++)

printf(

"%d

",mi[i]);

printf("\n

");for(int i=1;i<=cnt;i++)

printf(

"%d

",ma[i]);

}

單調佇列 滑動視窗

nkoj 2152 description 給你乙個長度為n n 10 6 的陣列,乙個長為k的滑動的窗體從最左移至最右端,你只能見到視窗的k個數,每次窗體向右移動一位,找出窗體所包含的數字的最大和最小值,如下表所示 k的值為3 視窗位置 最小值 最大值 1 3 1 3 5 3 6 7 1 3 1 ...

滑動視窗 單調佇列

給定乙個大小為n 106的陣列。有乙個大小為k的滑動視窗,它從陣列的最左邊移動到最右邊。您只能在視窗中看到k個數字。每次滑動視窗向右移動乙個位置。以下是乙個例子 該陣列為 1 3 1 3 5 3 6 7 k為3。視窗位置 最小值 最大值 1 3 1 3 5 3 6 7 1 3 1 3 1 3 5 3...

單調佇列 滑動視窗

p1886 滑動視窗 模板 單調佇列 有乙個長為 n 的序列 a,以及乙個大小為 k 的視窗。現在這個從左邊開始向右滑動,每次滑動乙個單位,求出每次滑動後視窗中的最大值和最小值。如果按照暴力方法做的話,每一次判斷相鄰的k個數的最大值和最小值,複雜度為o n k 肯定會超時,因此就想到把每次的最大值和...