P2801 教主的魔法

发布时间 2023-05-27 15:06:37作者: Zimo_666
点击查看代码
#include<bits/stdc++.h>
#define ls (k<<1)
#define rs (k<<1|1)
#define mid (l+r>>1)
#define int long long
using namespace std;
int n,m;
char opt;
const int N=1e6+7;
int s[N<<2],a[N],lazy[N<<2];
int maxx[N<<2],minn[N<<2];
void pushup(int k,int l,int r){
    maxx[k]=max(maxx[ls],maxx[rs]);
    minn[k]=min(minn[ls],minn[rs]);
}
void pushdown(int k,int l,int r){
    if(lazy[k]){
        lazy[ls]+=lazy[k];lazy[rs]+=lazy[k];
        maxx[ls]+=lazy[k];minn[ls]+=lazy[k];
        maxx[rs]+=lazy[k];minn[rs]+=lazy[k];
        lazy[k]=0;
    }
}
void build(int k,int l,int r){
    if(l==r) return maxx[k]=minn[k]=a[l],void();
    build(ls,l,mid);build(rs,mid+1,r);
    pushup(k,l,r);
}
void add(int k,int l,int r,int x,int y,int c){
    if(x<=l&&y>=r){
        maxx[k]+=c;minn[k]+=c;lazy[k]+=c;return;
    }
    pushdown(k,l,r);
    if(x<=mid) add(ls,l,mid,x,y,c);
    if(y>=mid+1) add(rs,mid+1,r,x,y,c);
    pushup(k,l,r);
}
int query(int k,int l,int r,int x,int y,int c){
    if(x<=l&&y>=r){
        if(c<=minn[k]) return r-l+1;
        if(c>maxx[k]) return 0;
    }
    pushdown(k,l,r);
    int ans=0;
    if(x<=mid) ans+=query(ls,l,mid,x,y,c);
    if(y>=mid+1) ans+=query(rs,mid+1,r,x,y,c);
    pushup(k,l,r);
    return ans;
}
signed main(){
	scanf("%lld%lld",&n,&m);
	for(int i=1;i<=n;i++)scanf("%lld",&a[i]);
	build(1,1,n);
    // cout<<query(1,1,n,1,n,5);
	for(int i=1;i<=m;i++){
	    int x,y;
        int c;
        cin>>opt>>x>>y>>c;
        
	    if(opt=='M'){
		    add(1,1,n,x,y,c);
	    }
	    else{printf("%lld\n",query(1,1,n,x,y,c));}
	}
    
	return 0;
}