样例没过求助
查看原帖
样例没过求助
343733
VickeyTugan楼主2021/8/27 18:12
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const ll N=1e5+10;
struct SegmentTree{
	ll l,r;//原序列对应左,右坐标 
	ll toAdd;
	ll toMul;
	ll sum; 
	ll len;
	#define len(x) tr[x].len
} tr[4*N];
ll a[N];
ll n,m,P;
void build(ll p,ll l,ll r){
	tr[p].l=l,tr[p].r=r;
	if(l==r){
		tr[p].sum=a[l];
		return ;
	}
	ll mid=(l+r)>>1;
	build(p*2,l,mid);
	build(p*2+1,mid+1,r);
	tr[p].sum=tr[p*2].sum+tr[p*2+1].sum;	
	tr[p].toMul=1;
	len(p)=r-l+1;
	return ;
}
void modP(ll x){
	tr[x].sum%=P;
	tr[x].toAdd%=P;
}
void pushdown(ll p){
	tr[p*2].toMul*=tr[p].toMul;
	tr[p*2].toAdd=tr[p*2].toAdd*tr[p].toMul+tr[p].toAdd;
	tr[p*2].sum=tr[p*2].sum*tr[p].toMul+len(p*2)*tr[p].toAdd;
	modP(p*2);
	tr[p*2+1].toMul*=tr[p].toMul;
	tr[p*2+1].toAdd=tr[p*2+1].toAdd*tr[p].toMul+tr[p].toAdd;
	tr[p*2+1].sum=tr[p*2+1].sum*tr[p].toMul+len(p*2+1)*tr[p].toAdd;
	modP(p*2+1);
	tr[p].toAdd=0;
	tr[p].toMul=1;
}
void add(ll l,ll r,ll t,ll k,ll p){
	if(l>tr[p].r||r<tr[p].l) return ;
	if(l<=tr[p].l&&r>=tr[p].r){
		if(t==1){
			tr[p].toMul*=k;
			tr[p].toAdd*=k;
			tr[p].sum*=k;
		}
		else{
			tr[p].toAdd+=k;
			tr[p].sum+=len(p)*k;
		}
		modP(p);
		return ;
	}
	pushdown(p);
	add(l,r,t,k,p*2);
	add(l,r,t,k,p*2+1);
	tr[p].sum=(tr[p*2].sum+tr[p*2+1].sum)%P;
	return ; 
}
ll rsq(ll l,ll r,ll p){
	if(tr[p].l>r||tr[p].r<l) return 0;
	if(tr[p].l>=l&&tr[p].r<=r) return tr[p].sum;
	pushdown(p);
	ll sum=rsq(l,r,p*2)+rsq(l,r,p*2+1);
	return sum%P; 
}
int main(){
	cin>>n>>m>>P;
	for(ll i=1;i<=n;i++)
		cin>>a[i];
	build(1,1,n);
	while(m--){
		ll op,x,y,k;
		cin>>op>>x>>y;	
		if(op!=3) {
			cin>>k;
			add(x,y,op,k,1);
		}
		else{
			cout<<rsq(x,y,1)<<endl;
		}
	}
	return 0;
}
2021/8/27 18:12
加载中...