分塊3 6279 數列分塊入門 3

2021-09-30 19:26:25 字數 1309 閱讀 2741

題目描述

給出乙個長為 nn 的數列,以及 nn 個操作,操作涉及區間加法,詢問區間內小於某個值 xx 的前驅(比其小的最大元素)。

輸入格式

第一行輸入乙個數字 nn。

第二行輸入 nn 個數字,第 ii 個數字為 a_iai​,以空格隔開。

接下來輸入 nn 行詢問,每行輸入四個數字 \mathrmopt、ll、rr、cc,以空格隔開。

若 \mathrm = 0opt=0,表示將位於 [l, r][l,r] 的之間的數字都加 cc。

若 \mathrm = 1opt=1,表示詢問 [l, r][l,r] 中 cc 的前驅的值(不存在則輸出 -1−1)。

輸出格式

對於每次詢問,輸出一行乙個數字表示答案。

樣例樣例輸入

4

1 2 2 3

0 1 3 1

1 1 4 4

0 1 2 2

1 1 2 4

樣例輸出 

3

-1

思路:第三題和第二題思路是樣的,因為是要找c的前驅,暴力找左右不完整塊的比c小最大值,再二分找完整塊比c小最大值,取其中最大即可。 

ac**:

#include#include#include#include#include#include#define inf 0x3f3f3f3f

using namespace std;

typedef long long ll;

const int maxn=1e5+10;

int s[maxn],flag[maxn],pos[maxn],ans,tag,n,m;

vectorv[1010];

void reset(int x)//用於對不完整塊排序

void update(int l,int r,int c)//更新值,第乙個操作

for(int i=pos[l]+1;i<=pos[r]-1;i++)//b陣列儲存完整塊的加值

flag[i]+=c;

}void query(int l,int r,int x)

}if(pos[l]!=pos[r])//暴力找右邊不完整塊 }}

for(int i=pos[l]+1;i<=pos[r]-1;i++)//整塊用二分查詢

}if(tag)

printf("%d\n",ans);

else

printf("-1\n");

}int main()

return 0;

}

(分塊)LOJ 6279 數列分塊入門 3

傳送門 loj 6279.數列分塊入門 3 題意 給出乙個長為n的數列,以及n個操作,操作涉及區間加法,詢問區間內小於某個值x的前驅 比其小的最大元素 以下引用hzwer大佬的解答 n 100000其實是為了區分暴力和一些常數較大的寫法。接著第二題的解法,其實只要把塊內查詢的二分稍作修改即可。不過這...

分塊4 6280 數列分塊入門 4

題目描述 給出乙個長為 nn 的數列,以及 nn 個操作,操作涉及區間加法,區間求和。輸入格式 第一行輸入乙個數字 nn。第二行輸入 nn 個數字,第 ii 個數字為 a iai 以空格隔開。接下來輸入 nn 行詢問,每行輸入四個數字 mathrmopt ll rr cc,以空格隔開。若 mathr...

數列分塊入門2

題目鏈結 給出乙個長為 n 的數列,以及 n 個操作,操作涉及區間加法,詢問區間內小於某個值 的元素個數。根據數列分塊入門1的思想,把n個數分為根號n塊,不完整塊的去暴力求和和查詢,完整塊用加法標進行標記,查詢排序後進行二分查詢。include include include include inc...