N个数,M个操作,操作有三类:
1. D,A,B,C 区间[a,b]中 所有数除以C,计算机整除
2. M,A,B,C 区间[a,b]所有数减去C
3. S,A,B 区间[a,b]求和,输出结果
注意
1.除法不能打lazy(计算机整除问题)而是更新到底,复杂度可以保证(log级别),因为很快降到0
2.注意减法与除法的融合
#include
#include
#include
#include
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
using namespace std;
typedef long long LL;
const int maxn=5e5+10;
LL sum[maxn<<2], add[maxn<<2];
bool flag[maxn<<2];
void push_up(int rt){
sum[rt]=sum[rt<<1]+sum[rt<<1|1];
flag[rt]=flag[rt<<1] | flag[rt<<1|1];
}
void push_down(int rt,int len){
if(add[rt]){
add[rt<<1]+=add[rt];
add[rt<<1|1]+=add[rt];
sum[rt<<1]+=add[rt]*(len-(len>>1));
sum[rt<<1|1]+=add[rt]*(len>>1);
add[rt]=0;
}
}
void build(int l,int r,int rt){
sum[rt]=add[rt]=0;
if(l==r){
scanf("%lld",&sum[rt]);
flag[rt]=(sum[rt]>0);
return;
}
int m=(l+r)>>1;
build(lson);
build(rson);
push_up(rt);
}
void Minus(int L,int R,int c,int l,int r,int rt){
if(L<=l&&r<=R){
add[rt]+=c;
sum[rt]+=(r-l+1)*c;
return;
}
push_down(rt,r-l+1);
int m=(l+r)>>1;
if(L<=m) Minus(L,R,c,lson);
if(R>m) Minus(L,R,c,rson);
push_up(rt);
}
void Division(int L,int R,int c,int l,int r,int rt){
if(flag[rt]==0) return;
if(l==r){
if(sum[rt]>0) sum[rt]/=(LL)c;
flag[rt]=(sum[rt]>0);
return;
}
push_down(rt,r-l+1);
int m=(l+r)>>1;
if(L<=m) Division(L,R,c,lson);
if(R>m) Division(L,R,c,rson);
push_up(rt);
}
LL Sum(int L,int R,int l,int r,int rt){
if(L<=l&&r<=R) return sum[rt];
push_down(rt,r-l+1);
int m=(l+r)>>1;
LL res = 0;
if(L<=m) res+=Sum(L,R,lson);
if(R>m) res+=Sum(L,R,rson);
return res;
}
int main(){
// freopen("D.in","r", stdin);
// freopen("test.out","w",stdout);
int T;
scanf("%d",&T);
for(int Case=1;Case<=T;Case++){
int n,m,a,b,c;
char op[10];
scanf("%d%d", &n,&m);
printf("Case %d:\n",Case);
build(1,n,1);
for(int i = 0;iscanf("%s",op);
if(op[0]=='D'){
scanf("%d%d%d",&a,&b,&c);
if(c==1) continue;
Division(a,b,c,1,n,1);
}
else if(op[0]=='M'){
scanf("%d%d%d",&a,&b,&c);
Minus(a,b,-c,1,n,1);
}
else{
scanf("%d%d",&a,&b);
LL res=Sum(a,b,1,n,1);
printf("%lld\n",res);
}
}
puts("");
}
return 0;
}