【线段树加乘】求助
查看原帖
【线段树加乘】求助
680022
Rice_Demon_King楼主2024/11/23 23:20

题目传送门
评测惨状10pts
代码如下:

//#pragma GCC optimize( 2 )
#include<bits/stdc++.h>
#define MAXN 100009
#define For(i,j,k) for(int i=j;i<=k;++i)
#define ll long long
using namespace std;
struct SegMentTree{
	int l,r;
	ll vulue;
	ll add_lzt,mul_lzt;
}tree[MAXN<<2];
int n,m;
ll p,a[MAXN];
void build(int now,int l,int r){
	tree[now].l=l,tree[now].r=r;
	tree[now].add_lzt=0ll,tree[now].mul_lzt=1ll; 
	if(l==r) tree[now].vulue=a[l];
	else{
		int mid=(l+r)>>1;
		build(now<<1,l,mid);
		build(now<<1|1,mid+1,r);
		tree[now].vulue=tree[now<<1].vulue+tree[now<<1|1].vulue;
	}
}
void multag(int now,ll c){
	tree[now].vulue*=c;
	tree[now].vulue%=p;
	tree[now].add_lzt*=c;
	tree[now].add_lzt%=p;
	tree[now].mul_lzt*=c;
}
void addtag(int now,ll c){
	tree[now].vulue+=(tree[now].r-tree[now].l+1)*c;
	tree[now].vulue%=p;
	tree[now].add_lzt+=c;
}
void push_down(int now){
	ll tmp1=tree[now].mul_lzt,tmp2=tree[now].add_lzt;
	multag(now<<1,tmp1);
	multag(now<<1|1,tmp1);
	tree[now].mul_lzt=1ll;
	addtag(now<<1,tmp2);
	addtag(now<<1|1,tmp2);
	tree[now].add_lzt=0ll;
}
void modify(int now,int l,int r,ll c,int op){
	int tl=tree[now].l,tr=tree[now].r;
	if(tl==l&&tr==r){
		if(op==1) multag(now,c);
		else addtag(now,c);
	}
	else{
		push_down(now);
		int mid=(tl+tr)>>1;
		if(r<=mid) modify(now<<1,l,r,c,op);
		else if(l>=mid+1) modify(now<<1|1,l,r,c,op);
		else modify(now<<1,l,mid,c,op),modify(now<<1|1,mid+1,r,c,op);
		tree[now].vulue=(tree[now<<1].vulue%p+tree[now<<1|1].vulue%p)%p;
	}
}
ll query(int now,int l,int r){
	int tl=tree[now].l,tr=tree[now].r;
	if(tl==l&&tr==r) return tree[now].vulue%p;
	else{
		push_down(now);
		int mid=(tl+tr)>>1;
		if(r<=mid) return query(now<<1,l,r)%p;
		else if(l>=mid+1) return query(now<<1|1,l,r)%p;
		else return (query(now<<1,l,mid)+query(now<<1|1,mid+1,r))%p;
	}
}
int main(){
	ios::sync_with_stdio(false);
	cin.tie(0);
	cout.tie(0);
	cin>>n>>p;
	For(i,1,n) cin>>a[i];
	build(1,1,n);
	cin>>m;
	while(m--){
		int op;
		cin>>op;
		if(op==1){
			int t,g;
			ll c;
			cin>>t>>g>>c;
			modify(1,t,g,c,1);
		}
		else if(op==2){
			int t,g;
			ll c;
			cin>>t>>g>>c;
			modify(1,t,g,c,2);
		}
		else{
			int t,g;
			cin>>t>>g; 
			cout<<query(1,t,g)<<endl;
		}
	}
	return 0;
}
2024/11/23 23:20
加载中...