一 核心:
f(x)=91 (x<=100)
f(x)=x-10 (x>100)
那么同一区间就可能不同的操作,那么该怎么解决呢?
我门直到同一区间的数据属于同一类别的时候再进行懒惰标记
区间记录最大值_max 最小值_min(同时应该有两个懒惰标记)
1) 最大值大于100 全部减去10
2)最小值小于等于100 全部变成91
注意懒惰标记的顺序,(2)应该在后面,想一想啊!
二 代码
1 /* 2 f(x)=91 (x<=100) 3 f(x)=x-10 (x>101) 4 */ 5 #include <bits/stdc++.h> 6 using namespace std; 7 #define lson l,m,rt*2 8 #define rson m+1,r,rt*2+1 9 const int N=1e5+7; 10 int sum[N*4],s[4*N],b[4*N]; 11 int t1[N*4],t2[N*4]; 12 int n,q; 13 void pushup (int rt) { 14 sum[rt]=sum[rt*2]+sum[rt*2+1]; 15 s[rt]=min (s[rt*2],s[rt*2+1]); 16 b[rt]=max (b[rt*2],b[rt*2+1]); 17 } 18 void cover (int r1,int r2,int k) { 19 t1[r2]+=t1[r1]; 20 sum[r2]-=k*10*t1[r1]; 21 s[r2]-=10*t1[r1]; b[r2]-=10*t1[r1]; 22 } 23 void c2 (int r1,int r2,int k) { 24 t2[r2]=1; 25 sum[r2]=91*k; 26 s[r2]=b[r2]=91; 27 } 28 void pushdown (int rt,int l,int r) { 29 int m=(l+r)/2; 30 if (t1[rt]) { 31 cover (rt,rt*2,m-l+1); 32 cover (rt,rt*2+1,r-m); 33 t1[rt]=0; 34 } 35 if (t2[rt]) { 36 c2 (rt,rt*2,m-l+1); 37 c2 (rt,rt*2+1,r-m); 38 t2[rt]=0; 39 } 40 return ; 41 } 42 void build (int l,int r,int rt) { 43 if (l==r) { 44 scanf ("%d",&sum[rt]); 45 s[rt]=b[rt]=sum[rt]; 46 return ; 47 } 48 int m=(l+r)/2; 49 build (lson); 50 build (rson); 51 pushup(rt); 52 return ; 53 } 54 void update (int L,int R,int l,int r,int rt) { 55 if (l>R||r<L) return ; 56 if (l>=L&&r<=R&&(s[rt]>100||b[rt]<=100)) { 57 if (s[rt]>100) { 58 sum[rt]-=(r-l+1)*10; 59 s[rt]-=10; b[rt]-=10; 60 t1[rt]++; 61 } 62 else if (b[rt]<=100) { 63 sum[rt]=(r-l+1)*91; 64 s[rt]=b[rt]=91; 65 t2[rt]=1; 66 } 67 return ; 68 } 69 int m=(l+r)/2; 70 pushdown (rt,l,r); 71 update (L,R,lson); 72 update (L,R,rson); 73 pushup (rt); 74 } 75 int query (int L,int R,int l,int r,int rt) { 76 if (r<L||l>R) return 0; 77 if (l>=L&&r<=R) return sum[rt]; 78 int m=(l+r)/2; 79 pushdown (rt,l,r); 80 return query (L,R,lson)+query (L,R,rson); 81 } 82 int main () 83 { 84 while (~scanf ("%d",&n)) { 85 memset (t1,0,sizeof(t1 )); 86 memset (t2,0,sizeof(t2)); 87 build (1,n,1); 88 scanf ("%d",&q); 89 for (int i=1;i<=q;i++) { 90 int op,l,r; 91 scanf ("%d %d %d",&op,&l,&r); 92 if (op==2) printf ("%d\n",query(l,r,1,n,1)); 93 else update (l,r,1,n,1); 94 } 95 } 96 return 0; 97 }
抓住青春的尾巴。。。