1. 程式人生 > >CF1039E Summer Oenothera Exhibition

CF1039E Summer Oenothera Exhibition

Summer Oenothera Exhibition

While some people enjoy spending their time solving programming contests, Dina prefers taking beautiful pictures. As soon as Byteland Botanical Garden announced Summer Oenothera Exhibition she decided to test her new camera there.

The exhibition consists of l=10100l=10^{100}

0100 Oenothera species arranged in a row and consecutively numbered with integers from 00 to l1l−1. Camera lens allows to take a photo of ww species on it, i.e. Dina can take a photo containing flowers with indices from xx to x+w1x+w−1 for some integer xx between 00 and lwl−w. We will denote such photo with [
x,x+w1][x,x+w−1]
.

She has taken nn photos, the ii-th of which (in chronological order) is [xi,xi+w1][x_i,x_i+w−1] in our notation. She decided to build a time-lapse video from these photos once she discovered that Oenothera blossoms open in the evening.

Dina takes each photo and truncates it, leaving its segment containing exactly k

k flowers, then she composes a video of these photos keeping their original order and voilà, a beautiful artwork has been created!

A scene is a contiguous sequence of photos such that the set of flowers on them is the same. The change between two scenes is called a cut. For example, consider the first photo contains flowers [1,5][1,5], the second photo contains flowers [3,7][3,7] and the third photo contains flowers [8,12][8,12]. If k=3k=3, then Dina can truncate the first and the second photo into [3,5][3,5], and the third photo into [9,11][9,11]. First two photos form a scene, third photo also forms a scene and the transition between these two scenes which happens between the second and the third photos is a cut. If k=4k=4, then each of the transitions between photos has to be a cut.

Dina wants the number of cuts to be as small as possible. Please help her! Calculate the minimum possible number of cuts for different values of kk.

Input

The first line contains three positive integer n,w,q(1n,q100000,1w109)n, w, q (1≤n,q≤100000, 1≤w≤10^9) — the number of taken photos, the number of flowers on a single photo and the number of queries.

Next line contains nn non-negative integers xi(0xi109)x_i (0≤x_i≤10^9) — the indices of the leftmost flowers on each of the photos.

Next line contains qq positive integers ki(1kiw)k_i (1≤k_i≤w) — the values of kk for which you have to solve the problem.

It’s guaranteed that all kik_i are distinct.

Output

Print qq integers — for each width of the truncated photo kik_i, the minimum number of cuts that is possible.

Examples
input

3 6 5 2 4 0 1 2 3 4 5

output

0 0 1 1 2

input

6 4 3 1 2 3 4 3 2 1 2 3

output

0 1 2

題目大意

直接看英文是真的不知道在說個什麼**玩意兒,但是修修告訴我題意是這樣的:

給定長度為nn的序列,常數ww,詢問次數qq

接下來qq組詢問,每次給出一個常數kik_i,求最少把序列分為多少段使得每段序列中數的極差不超過wkiw-k_i,輸出最小的段數1-1

題解

讓我們先考慮一下單次詢問怎麼做:直接貪心,每次儘量往後跳,直到極差不滿足條件為止,這樣我們就O(n)O(n)解決了一次詢問。

暴力跳太low\mathcal{low}了,不如我們倍增吧,先處理出最大/最小值的ST\mathcal{ST}表,我們就可以愉快的倍增往後跳了。

線上一看就很不可做的樣子,那就把所有詢問單增離線吧,離線之後,跳的距離也會單增,考慮維護每個點向後能跳到的最遠點nxt[v]nxt[v]

暴力一點的做法:對於一個新的極差rr,我們把所有點都嘗試往後挪來更新nxt[v]nxt[v],然後從頭開始往後沿著nxt[v]nxt[v]跳。

感覺這個操作修改和查詢都很爆炸,自然想到分塊一下,塊內路徑壓縮,更新路徑也僅限於塊內,塊之間跳用倍增來找。

複雜度?大概是O(n32log2n)O(n^{\frac{3}{2}}\log_2n)的吧。

據說修修有個O(O(n53+n43logn))O(O(n^{\frac{5}{3}} + n^{\frac{4}{3}}\log n))的優秀做法,然而我DZYOO(n32log2n)O(n^{\frac{3}{2}}\log_2n)CFCF最快,一手LCT\mathcal{LCT}彈飛綿羊代替路徑壓縮跑的飛快,吊錘所有演算法。

程式碼

ST\mathcal{ST}表表示2i2^i的維度一定要開在前面,這樣就能訪問連續記憶體,這大概就是AC\mathcal{AC}TLE\mathcal{TLE}的距離吧。

#include<bits/stdc++.h>
using namespace std;
const int M=1e5+5;
struct sd{int id,r;}ask[M<<6];
bool operator <(sd a,sd b){return a.r==b.r?a.id>b.id:a.r<b.r;}
int st[20][M][2],que[M],nxt[M],blo[M][2],jmp[M][2],ans[M],n,w,q,siz,tot;
void in()
{
	scanf("%d%d%d",&n,&w,&q);
	for(int i=1;i<=n;++i)scanf("%d",&que[i]),st[0][i][0]=st[0][i][1]=que[i];
	for(int i=1,k;i<=q;++i)scanf("%d",&k),ask[++tot]=(sd){i-q,w-k};
}
void up(int v){(nxt[v]==n+1||(nxt[v]-1)%siz==0)?(jmp[v][0]=1,jmp[v][1]=v):(jmp[v][0]=jmp[nxt[v]][0]+1,jmp[v][1]=jmp[nxt[v]][1]);}
void ac()
{
	for(;siz*siz*siz<6*n;++siz);
	for(int j=1;(1<<j)<=n;++j)for(int i=1;i+(1<<j)<=n+1;++i)
	st[j][i][0]=min(st[j-1][i][0],st[j-1][i+(1<<j-1)][0]),
	st[j][i][1]=max(st[j-1][i][1],st[j-1][i+(1<<j-1)][1]);
	for(int i=n;i>=1;--i)
	{
		nxt[i]=i+1,blo[i][0]=blo[i][1]=que[i],up(i);
		for(int j=i+1,mn=que[i],mx=que[i];j<=n&&(j-1)%siz>0;++j)mn=min(mn,que[j]),mx=max(mx,que[j]),ask[++tot]=(sd){i,mx-mn};
	}
	sort(ask+1,ask+1+tot);
	for(int i=1,pos,cst,mn,mx,k,to,maxn,minn;i<=tot;++i)
	if(ask[i].id<=0)for(pos=1,cst=-1;pos<=n;ans[ask[i].id+q]=cst)
	{
		cst+=jmp[pos][0],pos=jmp[pos][1],mn=blo[pos][0],mx=blo[pos][1],to=pos,k=0;
		for(;pos+(1<<k)<=n+1&&(maxn=max(mx,st[k][pos][1]))-(minn=min(mn,st[k][pos][0]))<=ask[i].r;++k)mx=maxn,mn=minn;
		for(;k--;)if(to+(1<<k)<=n+1&&(maxn=max(mx,st[k][to
            
           

相關推薦

[CF1039E]Summer Oenothera Exhibition[根號分治+lct]

題意 給一個長度為 \(n\) 的序列, \(q\) 次詢問,次給一個 \(k_i\) ,問最少將序列劃分成多少次,滿足每一段的極差不超過\(w−k_i\). \(1 \leq n, q \leq 10^5, 1 \leq w \leq 10^9,1 \leq k_i \leq w,0 \leq x_i

CF1039E Summer Oenothera Exhibition

Summer Oenothera Exhibition While some people enjoy spending their time solving programming contests, Dina prefers taking beautif

CF1039E Summer Oenothera Exhibition 貪心、分治、倍增

傳送門 感謝這一篇部落格的指導(Orzwxh) $PS$:預設陣列下標為$1$到$N$ 首先很明顯的貪心:每一次都選擇儘可能長的區間 不妨設$d_i$表示在取當前$K$的情況下,左端點為$i$的所有滿足條件的區間中最大的右端點$+1$,然後連邊$(i,d_i)$ 那麼我們就需要求一條鏈的長度,並

Codeforces 1039E:Summer Oenothera Exhibition(LCT)

傳送門 題解: 首先可以貪心O(n)O(n)解決單次詢問。 考慮優化,每個點有一個後繼,這個後繼在≤n−−√≤n的時候,我們暴力修改,否則不管。 查詢直接在LCT上查詢O(n−−√)O(n)次即可。 時間複雜度O(nn−−√logn)O(nnlog⁡n)

2017 Pre-summer Training I - Searching and Strings

strlen .com event 分享 ddn char c++ esp style B. 單詞替換(KMP + Lazy標記) Sample Input 3 aaa a b aaa aa b ababa aba cd Sample Outpu

HDU-1827 Summer Holiday

div std scan 過去 hdu summer map output script To see a World in a Grain of Sand And a Heaven in a Wild Flower, Hold Infinity in the pal

bzoj4104 [Thu Summer Camp 2015]解密運算

sort sign include 走了 space friend def static none 傳送門:http://www.lydsy.com/JudgeOnline/problem.php?id=4104 【題解】 腦洞+找規律做出來的。。 我用樣例作為說明吧 樣例

Gym 100733J Summer Wars 題解:靈活運用掃描線的思想

ace ng- 最大值 掃描線 例如 main post 集合 i++ 題意: 給你n個點,m個橫著的線段。你能夠橫移這些線段,可是這些線段的相對位置不能改變。假設一個點,在它的正上方和和正下方都有線段(包含線段的終點)。則這個點被視為被“屏蔽”。問通過隨意平移我們

SDKD 2017 Summer Single Training #03

應該 簡單 做的 註意 擲骰子 for com -o 難點 今天的題目有 6 個。 第一題: CodeForces - 400D Dima and Bacteria 這個題實際是不難的,難的可能在題意的理解上還有題幹有點長,這個題很考察題意上面,知識點很熟悉,並查集和Fl

Summer training #2

一個 chang hang char summer nbsp bsp 操作數 ini A:不管有沒有負數 一頓操作之後肯定只有正數 又因為A=A-B 所以最大值是一直在減小的 所以一定有結果 B:..一開始以為求min操作數 WA了2發 直接求所有數的GCD如果所有數的GC

2017ecjtu-summer training #4 UESTC 30

() -- can 最短路 review java mem stream iostream 最短路

2017ecjtu-summer training #3 POJ3264

algo math lis 數組 from ger %d 最大 sent

Summer training #6

its else b- color 線下 con 分享 oid 模擬 A:水.看0多還是1多就行 B:模擬二進制運算 ,,卡了好久 不應該 #include <bits/stdc++.h> #include <cstring> #include

2017ecjtu-summer training #5 UVA10382

int 分享 mage stream color ges -1 return 貪心 題意 問最少可用幾個圓覆蓋矩形區域。 解析 將圓形轉換成矩形有效區域,直徑小於等於寬度的圓不考慮,從而轉化成區間覆蓋問題,然後貪心出最少圓。 貪心思想 每次選擇出區域左界比上次選出的

Summer training #7

+= -- %d aps ner fff time imm clas B:讀懂題意模擬 #include <bits/stdc++.h> #include <cstring> #include <iostream> #include

2017ecjtu-summer training # 9 HDU 4544

end sam 計算 log 每次 () 大於等於 降序排序 operator 湫湫系列故事——消滅兔子 Time Limit: 3000/1000 MS (Java/Others) Memory Limit: 65535/32768 K (Java/Others)T

臺州 OJ 5072 Cow Exhibition 01背包

可能 put () string log 滾動 bsp pan max 給出 n 頭牛,每頭牛有兩個屬性 smartness 和 funness ,求從所有的牛裏選一些牛,使這些牛的 smartness + funness 的和最大,且 smartness 的和、funne

2017ecjtu-summer training #1 UVA 10399

stopped keep ger time style 一個 blog code stdlib.h It has been said that a watch that is stopped keeps better time than one that loses 1 s

2017ecjtu-summer training #7 POJ 2689

ble ac代碼 pre mat itself not sin pri stream Prime Distance Time Limit: 1000MS Memory Limit: 65536K Total Submissions: 18731 Acce

Summer training round2 #1

mat line play 錯排 fine pre 位置 用兩個 none A:水 B:求兩個三角形之間的位置關系:相交 相離 內含 ①用三個點是否在三角形內外判斷 計算MA*MB、MB*MC、MC*MA的大小 若這三個值同號,那麽在三角形的內部,異號在外部 #i