LOJ #6283. 數列分塊入門 7-分塊(區間乘法、區間加法、單點查詢)


內存限制:256 MiB時間限制:500 ms標准輸入輸出
題目類型:傳統評測方式:文本比較
上傳者: hzwer

題目描述

給出一個長為 nn 的數列,以及 nn 個操作,操作涉及區間乘法,區間加法,單點詢問。

輸入格式

第一行輸入一個數字 nn。

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

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

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

若 \mathrm{opt} = 1opt=1,表示將位於 [l, r][l,r] 的之間的數字都乘 cc。

若 \mathrm{opt} = 2opt=2,表示詢問 a_rar 的值 \mathop{\mathrm{mod}} 10007mod10007(ll 和 cc 忽略)。

輸出格式

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

樣例

樣例輸入

7
1 2 2 3 9 3 2
0 1 3 1
2 1 3 1
1 1 4 4
0 1 7 2
1 2 6 4
1 1 6 5
2 2 6 4

樣例輸出

3
100

數據范圍與提示

對於 100\%100% 的數據,1 \leq n \leq 100000, -2^{31} \leq \mathrm{others}1n100000,231others、\mathrm{ans} \leq 2^{31}-1ans2311。

 

這道題要開比1e5大,要不然過不去,真實測試。。。

 

代碼:

  1 //#6283. 數列分塊入門 7-區間乘法,區間加法,單點查詢-要開1e6,mdzz
  2 #include<bits/stdc++.h>
  3 using namespace std;
  4 typedef long long ll;
  5 const int maxn=1e6+10;
  6 
  7 int n,m;
  8 int a[maxn],add[maxn],mul[maxn],pos[maxn];
  9 const int mod=10007;
 10 
 11 void update_add(int l,int r,int c)
 12 {
 13     if(pos[l]==pos[r]){
 14         for(int i=(pos[l]-1)*m+1;i<=pos[l]*m;i++){
 15             a[i]=(a[i]*mul[pos[l]]%mod+add[pos[l]]+mod)%mod;
 16         }
 17         for(int i=l;i<=r;i++)
 18             a[i]=(a[i]+c+mod)%mod;
 19         mul[pos[l]]=1;add[pos[l]]=0;
 20     }
 21     else{
 22         for(int i=(pos[l]-1)*m+1;i<=pos[l]*m;i++){
 23             a[i]=(a[i]*mul[pos[l]]%mod+add[pos[l]]+mod)%mod;
 24         }
 25         for(int i=l;i<=pos[l]*m;i++)
 26             a[i]=(a[i]+c+mod)%mod;
 27         mul[pos[l]]=1;add[pos[l]]=0;
 28         for(int i=pos[l]+1;i<pos[r];i++){
 29             add[i]=(add[i]+c+mod)%mod;
 30         }
 31         for(int i=(pos[r]-1)*m+1;i<=min(pos[r]*m,n);i++){
 32             a[i]=(a[i]*mul[pos[r]]%mod+add[pos[r]]+mod)%mod;
 33         }
 34         for(int i=(pos[r]-1)*m+1;i<=r;i++)
 35             a[i]=(a[i]+c+mod)%mod;
 36         mul[pos[r]]=1;add[pos[r]]=0;
 37     }
 38 }
 39 
 40 void update_mul(int l,int r,int c)
 41 {
 42     if(pos[l]==pos[r]){
 43         for(int i=(pos[l]-1)*m+1;i<=pos[l]*m;i++){
 44             a[i]=(a[i]*mul[pos[l]]%mod+add[pos[l]]+mod)%mod;
 45         }
 46         for(int i=l;i<=r;i++)
 47             a[i]=(a[i]*c+mod)%mod;
 48         mul[pos[l]]=1;add[pos[l]]=0;
 49     }
 50     else{
 51         for(int i=(pos[l]-1)*m+1;i<=pos[l]*m;i++){
 52             a[i]=(a[i]*mul[pos[l]]%mod+add[pos[l]]+mod)%mod;
 53         }
 54         for(int i=l;i<=pos[l]*m;i++)
 55             a[i]=(a[i]*c+mod)%mod;
 56         mul[pos[l]]=1;add[pos[l]]=0;
 57         for(int i=pos[l]+1;i<pos[r];i++){
 58             add[i]=(add[i]*c+mod)%mod;
 59             mul[i]=(mul[i]*c+mod)%mod;
 60         }
 61         for(int i=(pos[r]-1)*m+1;i<=min(pos[r]*m,n);i++){
 62             a[i]=(a[i]*mul[pos[r]]%mod+add[pos[r]]+mod)%mod;
 63         }
 64         for(int i=(pos[r]-1)*m+1;i<=r;i++)
 65             a[i]=(a[i]*c+mod)%mod;
 66         mul[pos[r]]=1;add[pos[r]]=0;
 67     }
 68 }
 69 
 70 int main()
 71 {
 72     scanf("%d",&n);
 73     m=sqrt(n);
 74     for(int i=1;i<=n;i++){
 75         scanf("%d",&a[i]);
 76         a[i]%=mod;
 77         pos[i]=(i-1)/m+1;
 78         mul[pos[i]]=1;
 79         add[pos[i]]=0;
 80     }
 81     for(int i=1;i<=n;i++){
 82         int op,l,r,c;
 83         scanf("%d%d%d%d",&op,&l,&r,&c);
 84         c%=mod;
 85         if(op==0){
 86             update_add(l,r,c);
 87         }
 88         else if(op==1){
 89             update_mul(l,r,c);
 90         }
 91         else if(op==2){
 92             printf("%d\n",(a[r]*mul[pos[r]]+add[pos[r]])%mod);
 93         }
 94     }
 95 }
 96 
 97 
 98 /*
 99 10
100 1 3 4 2 5 7 11 3 5 1
101 0 1 5 1
102 1 1 7 2
103 2 3 9 1
104 0 4 8 1
105 1 1 5 2
106 1 3 5 2
107 2 5 7 1
108 1 3 5 2
109 2 2 3 2
110 2 3 4 5
111 
112 5
113 23
114 80
115 56
116 */

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM