样例没过求调
查看原帖
样例没过求调
761649
ryf_loser楼主2023/10/8 22:40

应该是 pushdown 的问题,但是蒟蒻调不出来,请大佬们指正!!!

#include<cstdio>
#include<algorithm>
using namespace std;
#define lll long long
inline lll in(){
	lll x=0,f=1;char c;
	c=getchar();
	while (c<'0'||c>'9'){
		if (c=='-')f=-1;
		c=getchar();
	}
	while (c>='0'&&c<='9'){x=(x<<3)+(x<<1)+(c^48);c=getchar();}
	return x*f;
}
int n,m,q;
lll a[100005];
struct node{lll val,add,mul;}tree[400005];
inline void build(int k,int l,int r){
	tree[k].mul=1;
	if (l==r){tree[k].val=a[l];return ;}
	int mid=l+r>>1;
	build(k<<1,l,mid);
	build(k<<1|1,mid+1,r);
	tree[k].val=(tree[k<<1].val+tree[k<<1|1].val)%m;
}
inline void pushdown(int k,int l,int r){
	int mid=l+r>>1;
	tree[k<<1].val=(tree[k<<1].val*tree[k].mul+tree[k].add*(mid-l+1))%m;
	tree[k<<1|1].val=(tree[k<<1|1].val*tree[k].mul+tree[k].add*(r-mid))%m;
	tree[k<<1].mul=tree[k<<1].mul*tree[k].mul%m;
	tree[k<<1|1].mul=tree[k<<1|1].mul*tree[k].mul%m;
	tree[k<<1].add=(tree[k<<1].add*tree[k].mul%m+tree[k].add)%m;
	tree[k<<1|1].add=(tree[k<<1|1].add*tree[k].mul%m+tree[k].add)%m;
	tree[k].mul=1;tree[k].add=0;
}
inline void update1(int k,int l,int r,int ll,int rr,long long x){
	if (ll<=l&&r<=rr){
		tree[k].val=(tree[k].val*x)%m;
		tree[k].add=(tree[k].add*x)%m;
		tree[k].mul=(tree[k].mul*x)%m;
		return ;
	}
	pushdown(k,l,r);
	int mid=l+r>>1;
	if (ll<=mid)update1(k<<1,l,mid,ll,rr,x);
	if (rr>mid)update1(k<<1|1,mid+1,r,ll,rr,x);
	tree[k].val=(tree[k<<1].val+tree[k<<1|1].val)%m;
}
inline void update2(int k,int l,int r,int ll,int rr,long long x){
	if (ll<=l&&r<=rr){
		tree[k].val=(tree[k].val+x*(r-l+1)%m)%m;
		tree[k].add=(tree[k].add+x)%m;
		return ;
	}
	pushdown(k,l,r);
	int mid=l+r>>1;
	if (ll<=mid)update2(k<<1,l,mid,ll,rr,x);
	if (rr>mid)update2(k<<1|1,mid+1,r,ll,rr,x);
	tree[k].val=(tree[k<<1].val+tree[k<<1|1].val)%m;
}
inline lll ask(int k,int l,int r,int ll,int rr){
	if (ll<=l&&r<=rr)return tree[k].val;
	int mid=l+r>>1;
	lll ans=0;
	if (ll<=mid)ans+=ask(k<<1,l,mid,ll,rr);
	if (rr>mid)ans+=ask(k<<1|1,mid+1,r,ll,rr);
	ans%=m;
	return ans;
}
int main(){
	n=in(),q=in(),m=in();
	for (int i=1;i<=n;i++)a[i]=in()%m;
	build (1,1,n);
	while (q--){
		int op=in(),x=in(),y=in();
		if (op==1)update1(1,1,n,x,y,in());
		else if (op==2)update2(1,1,n,x,y,in());
		else printf ("%lld\n",ask(1,1,n,x,y));
	}
	return 0;
}
2023/10/8 22:40
加载中...