tyvj4875 排列(單調棧)

2021-08-08 19:45:02 字數 961 閱讀 5096

既然是讓我兩天都想不明白的題,就寫總結吧。

題面題意:給你乙個n個數的隨機排列,設ans[k]為區間內(最大值-最小值)≤k的區間個數。

求ans[0~n-1]。

暴力就是固定左端點,右端點不斷向右拓展,用得到的新數來更新當前最大值與最小值。

實際操作中,我們發現很多次拓展都不能更新最大值與最小值。

就萌發出乙個玄學優化:每次直接跳到能更新最大值或最小值的點,然後統計答案。

這用兩個單調棧即可預處理出每個點右邊第乙個比它大(小)的數。

然後據說由於這是乙個隨機排列,有證明這樣就是o(nlogn)的。

#include 

#include

#include

#include

#include

#include

#include

#include

using

namespace

std;

#define mmst(a, b) memset(a, b, sizeof(a))

#define mmcp(a, b) memcpy(a, b, sizeof(b))

typedef

long

long ll;

const

int n=100100;

int t,n,a[n];

int big[n],small[n];

int st1[n],l1,st2[n],l2;

long

long ans[n];

int main()

for(int i=1;i<=n;i++)}}

cout

<0]=n;

for(int i=1;i1];

printf("%lld\n",ans[i]);}}

return

0;}

tyvj4875 排列(單調棧)

傳送門 自從比賽我打錯了這題的60分暴力後,我幼小的內心中留下了一道陰影。多組資料一定要記得清空全域性變數和陣列啊啊啊!甚至為了吸取教訓,我還準備專門寫一篇。這題的60分做法就是固定左端點,隨著右端點的右移更新最值並貢獻答案。考慮100分的做法,當時良久都不知道怎麼做,都在想有什麼資料結構能大顯神通...

hdu 1716 排列2 排列組合

問題描述 ray又對數字的列產生了興趣 現有四張卡片,用這四張卡片能排列出很多不同的4位數,要求按從小到大的順序輸出這些4位數 input 每組資料佔一行,代表四張卡片上的數字 0 數字 9 如果四張卡片都是0,則輸入結束。output 對每組卡片按從小到大的順序輸出所有能由這四張卡片組成的4位數,...

197 排列序號

是 這道題採取暴力解法會超時,應當對於原陣列的每乙個位置找到其後有多少個數比它小,然後再相加這些數與對應的權的成績。class solution long long ans 1,fac 1,cc 1 for int i len 2 i 0 i ans fac cc c i return ans 注意...