线段树过不了样例,求调(悬关)
查看原帖
线段树过不了样例,求调(悬关)
715233
Dino_chx楼主2023/4/10 17:52
#include<bits/stdc++.h>
#define ll long long
using namespace std;
const int N=1e5+7;
int n,m,p;
struct ST
{
	int l,r;
	ll sum,addtag,multag;
}tree[N<<2];
int a[N];
void pushup(int x)
{
	tree[x].sum=(tree[x<<1].sum+tree[x<<1|1].sum)%p;
	return;
}
void build(int x,int l,int r)
{
	tree[x]={l,r};
	if(l==r)
	{
		tree[x]={a[l]%p,0,1};
		return;
	}
	int mid=l+r>>1;
	build(x<<1,l,mid);
	build(x<<1|1,mid+1,r);
	pushup(x);
	return; 
}
void pushdown(int x)
{
	ST &rt=tree[x],&ls=tree[x<<1],&rs=tree[x<<1|1];
	if(rt.multag!=1)
	{
		ls.multag=ls.multag*rt.multag%p;
		rs.multag=rs.multag*rt.multag%p;
		ls.addtag=ls.addtag*rt.multag%p;
		rs.addtag=rs.addtag*rt.multag%p;
		ls.sum=ls.sum*rt.multag%p;
		rs.sum=rs.sum*rt.multag%p;
		rt.multag=1; 
	}
	if(rt.addtag)
	{
		ls.addtag=(ls.addtag+rt.addtag)%p;
		rs.addtag=(rs.addtag+rt.addtag)%p;
		ls.sum=(ls.sum+rt.addtag)%p;
		rs.sum=(rs.sum+rt.addtag)%p;
		rt.addtag=0; 
	}
	return;
}
void add(int x,int l,int r,int k)
{
	if(tree[x].l>=l&&tree[x].r<=r)
	{
		tree[x].addtag+=k;
		tree[x].addtag%=p;
		tree[x].sum+=(tree[x].r-tree[x].l+1)*k%p;
		return;
	}
	pushdown(x);
	int mid=tree[x].l+tree[x].r>>1;
	if(l<=mid)
	add(x<<1,l,r,k);
	if(r>mid)
	add(x<<1|1,l,r,k);
	pushup(x);
	return;
} 
void multi(int x,int l,int r,int k)
{
	if(tree[x].l>=l&&tree[x].r<=r)
	{
		tree[x].addtag=tree[x].addtag*k%p;
		tree[x].multag=tree[x].multag*k%p;
		tree[x].sum=tree[x].sum*k%p;
		return;
	}
	pushdown(x);
	int mid=tree[x].l+tree[x].r>>1;
	if(l<=mid)
	multi(x<<1,l,r,k);
	if(r>mid)
	multi(x<<1|1,l,r,k);
	pushup(x);
	return;
}
ll query(int x,int l,int r)
{
	if(tree[x].l>=l&&tree[x].r<=r)
	return tree[x].sum;
	pushdown(x);
	ll ans=0;
	int mid=tree[x].l+tree[x].r>>1;
	if(l<=mid)
	ans=(ans+query(x<<1,l,r))%p;
	if(r>mid)
	ans=(ans+query(x<<1|1,l,r))%p;
	return ans%p; 
}
int main()
{
	scanf("%d%d%d",&n,&m,&p);
	for(int i=1;i<=n;i++)
	{
		scanf("%d",&a[i]);
	}
	build(1,1,n);
	while(m--)
	{
		int op,x,y,k;
		scanf("%d%d%d",&op,&x,&y);
		if(op==1)
		{
			scanf("%d",&k);
			add(1,x,y,k);
		}
		if(op==2)
		{
			scanf("%d",&k);
			multi(1,x,y,k);
		}
		if(op==3)
		printf("%d\n",query(1,x,y)%p);
	}
	return 0;	
} 
2023/4/10 17:52
加载中...