bzoj1798维护序列
暴力数据结构之线段树$qwq$
裸题直接敲板子
忘了啥时候写的了$qwq$
直接上代码吧
/************************************************************** Problem: 1798 User: zhangheran Language: C++ Result: Accepted Time:6372 ms Memory:10688 kb ****************************************************************/ #include<cstdio> #include<iostream> #include<algorithm> using namespace std; typedef long long ll; int n; int m; long long mod; struct lt { long long val[400010]; long long lazy[400010]; long long lazzy[400010]; inline void update(int p,int l,int r) { val[p]*=lazzy[p]; val[p]%=mod; val[p]+=lazy[p]*(r-l); val[p]%=mod; return; } inline void pushdown(int p,int l,int r) { update(p,l,r); if(r-l>1) { lazy[2*p]*=lazzy[p]; lazy[2*p]+=lazy[p]; lazy[2*p]%=mod; lazzy[2*p]*=lazzy[p]; lazzy[2*p]%=mod; lazy[2*p+1]*=lazzy[p]; lazy[2*p+1]+=lazy[p]; lazy[2*p+1]%=mod; lazzy[2*p+1]*=lazzy[p]; lazzy[2*p+1]%=mod; }lazy[p]=0; lazzy[p]=1; return; } ll build(int p,int l,int r) { lazzy[p]=1; if(r-l==1) { scanf("%lld",&val[p]); val[p]%=mod; return val[p]; } int mid=(l+r)/2; if(mid>l)val[p]+=build(2*p,l,mid); if(mid<r)val[p]+=build(2*p+1,mid,r); val[p]%=mod; return val[p]; } void setplus(int p,int l,int r,int dl,int dr,long long plus) { if(lazy[p]!=0||lazzy[p]!=1) pushdown(p,l,r); if(l==dl&&r==dr) { lazy[p]+=plus; lazy[p]%=mod; pushdown(p,l,r); return; } int mid=(l+r)/2; if(mid>dl) setplus(2*p,l,mid,dl,min(mid,dr),plus); else pushdown(2*p,l,mid); if(mid<dr) setplus(2*p+1,mid,r,max(mid,dl),dr,plus); else pushdown(2*p+1,mid,r); val[p]=(val[2*p]+val[2*p+1])%mod; return; } void setmult(int p,int l,int r,int dl,int dr,long long mult) { if(lazzy[p]!=1||lazy[p]!=0)pushdown(p,l,r); if(l==dl&&r==dr) { lazy[p]*=mult; lazzy[p]*=mult; lazy[p]%=mod; lazzy[p]%=mod; pushdown(p,l,r); return; } int mid=(l+r)/2; if(mid>dl) setmult(2*p,l,mid,dl,min(mid,dr),mult); else pushdown(2*p,l,mid); if(mid<dr)setmult(2*p+1,mid,r,max(mid,dl),dr,mult); else pushdown(2*p+1,mid,r); val[p]=(val[2*p]+val[2*p+1])%mod; return; } ll sum(int p,int l,int r,int dl,int dr) { if(lazy[p]!=0||lazzy[p]!=1) pushdown(p,l,r); if(l==dl&&r==dr) return val[p]; int mid=(l+r)/2; ll res=0; if(mid>dl) res+=sum(2*p,l,mid,dl,min(mid,dr)); if(mid<dr) res+=sum(2*p+1,mid,r,max(mid,dl),dr); res%=mod; return res; } }lt; int main() { scanf("%d%d",&n,&mod); lt.build(1,0,n);scanf("%d",&m); for(int i=1;i<=m;i++) { int opt,u,v; scanf("%d%d%d",&opt,&u,&v); if(opt==1) { int t; scanf("%d",&t); lt.setmult(1,0,n,u-1,v,t); } else if(opt==2) { int t; scanf("%d",&t); lt.setplus(1,0,n,u-1,v,t); } else if(opt==3) printf("%lld\n",lt.sum(1,0,n,u-1,v)); } return 0; }