社区讨论
线段书2求助
灌水区参与者 1已保存回复 0
讨论操作
快速查看讨论及其快照的属性,并进行相关操作。
- 当前回复
- 0 条
- 当前快照
- 1 份
- 快照标识符
- @m39uht6t
- 此快照首次捕获于
- 2024/11/09 15:29 去年
- 此快照最后确认于
- 2025/11/04 15:03 4 个月前
CPP
#include <bits/stdc++.h>
using namespace std;
struct node{
long long p,c;
}tax[400005];
int n,q,k;
long long mod;
struct node2{
int l,r;
long long sum;
}tree[400005];
long long a[100005];
void build(int l,int r,int x){
if(r==l){
tree[x].sum=a[l];
tree[x].l=l;
tree[x].r=r;
return ;
}
int mid=(l+r)/2;
build(l,mid,x*2);
build(mid+1,r,x*2+1);
tree[x].sum=(tree[x*2].sum+tree[x*2+1].sum)%mod;
}
void push_down(int l,int r,int x){
if(tax[x].c!=0){
tax[x*2].c*=tax[x].c;
tax[x*2].c%=mod;
tax[x*2+1].c*=tax[x].c;
tax[x*2+1].c%=mod;
tree[x*2].sum=tree[x*2].sum*tax[x].c%mod;
tree[x*2+1].sum=tree[x*2+1].sum*tax[x].c%mod;
}
if(tax[x].p!=0){
tax[x*2].p+=tax[x].p;
tax[x*2+1].p+=tax[x].p;
tree[x*2].sum+=tax[x].p*(tree[x*2].r-tree[x*2].l+1);
tree[x*2+1].sum+=tax[x].p*(tree[x*2+1].r-tree[x*2+1].l+1);
}
tax[x].c=1;
tax[x].p=0;
}
void add1(int l,int r,int a,int b,int x){
if(a<=l && r<=b){
push_down(l,r,x);
tax[x].p+=k;
tax[x].p%=mod;
tree[x].sum+=k*(r-l+1);
tree[x].sum%=mod;
return ;
}
push_down(l,r,x);
int mid=(l+r)/2;
if(mid>=a) add1(l,mid,a,b,x*2);
if(mid<b) add1(mid+1,r,a,b,x*2+1);
tree[x].sum=(tree[x*2].sum+tree[x*2+1].sum)%mod;
}
void add2(int l,int r,int a,int b,int x){
if(a<=l && r<=b){
push_down(l,r,x);
tax[x].c*=k;
tax[x].c%=mod;
tree[x].sum*=k;
tree[x].sum%=mod;
return ;
}
push_down(l,r,x);
int mid=(l+r)/2;
if(mid>=a) add2(l,mid,a,b,x*2);
if(mid<b) add2(mid+1,r,a,b,x*2+1);
tree[x].sum=(tree[x*2].sum+tree[x*2+1].sum)%mod;
}
long long merge(int l,int r,int a,int b,int x){
if(a<=l && r<=b){
push_down(l,r,x);
return tree[x].sum;
}
push_down(l,r,x);
int mid=(l+r)/2;
long long ret=0;
if(mid>=a) ret+=merge(l,mid,a,b,x*2);
if(mid<b) ret+=merge(mid+1,r,a,b,x*2+1);
ret%=mod;
return ret%mod;
}
int main(){
scanf("%d%d%lld",&n,&q,&mod);
for(int i=1;i<=n;i++){
scanf("%d",&a[i]);
}
build(1,n,1);//cerr<<"aaa";
int a,b,t;
for(int i=1;i<=q;i++){
scanf("%d%d%d",&t,&a,&b);
if(t==2){
scanf("%d",&k);
add1(1,n,a,b,1);
cout<<merge(1,n,a,b,1)<<endl;
}else if(t==1){
scanf("%d",&k);
add2(1,n,a,b,1);
cout<<merge(1,n,a,b,1)<<endl;
}else{
cout<<merge(1,n,a,b,1)<<endl;
}
}
return 0;
}/*
5 5 10000
1 1 1 1 1
2 1 4 5
1 2 5 2
*/
回复
共 0 条回复,欢迎继续交流。
正在加载回复...