救救孩子吧!!
  • 板块灌水区
  • 楼主MuYC
  • 当前回复0
  • 已保存回复0
  • 发布时间2020/10/15 11:55
  • 上次更新2023/11/5 10:44:22
查看原帖
救救孩子吧!!
67817
MuYC楼主2020/10/15 11:55
#include <bits/stdc++.h>
using namespace std;
#define int long long 
int Mod,n,m;
int a[200005];
struct tree{int l,r,sum,laza,lazb;}T[800005];
void build_tree(int x,int l,int r){
	T[x].l = l,T[x].r = r;
	T[x].lazb = 1;T[x].laza = 0;
	if(T[x].l == T[x].r){T[x].sum = a[l];return ;}
	int mid = (l + r) >> 1;
	build_tree(x*2,l,mid);
	build_tree(x*2+1,mid + 1,r);
	T[x].sum = T[x*2].sum + T[x*2+1].sum;
	return ;
}
void ad(int x,int k1,int k2){
	k1 %= Mod , k2 %= Mod;
	T[x].sum = (T[x].sum % Mod * k2 % Mod + ((T[x].r - T[x].l + 1)*k1) % Mod) % Mod ;
	T[x].laza *= k2;T[x].laza %= Mod;
	T[x].laza += k1;T[x].laza %= Mod;
	T[x].lazb *= k2;T[x].lazb %= Mod;
	return ;
}
void pushdown(int x){
	if(T[x].laza == 0 && T[x].lazb == 0)return ;
	ad(x*2,T[x].laza,T[x].lazb);
	ad(x*2+1,T[x].laza,T[x].lazb);
	T[x].laza = 0 ,T[x].lazb = 1;
	return ;
}
int get(int x,int l,int r){
	if(T[x].l >= l && T[x].r <= r)return T[x].sum % Mod;
	pushdown(x);
	int ans = 0 , mid = (T[x].l + T[x].r) >> 1;
	if(l <= mid)ans += get(x*2,l,r),ans %= Mod;
	if(r  > mid)ans += get(x*2+1,l,r),ans %= Mod;
	return ans % Mod;
}
void change(int x,int l,int r,int k,int op){
	if(l <= T[x].l && r >= T[x].r){
		if(op == 1)
			ad(x,0,k);
		else ad(x,k,1);
		return ;
	}
	pushdown(x);
	int mid = (T[x].l + T[x].r) >> 1;
	if(l <= mid)change(x*2,l,r,k,op);
	if(r >  mid)change(x*2+1,l,r,k,op);
	T[x].sum = T[x*2+1].sum + T[x*2].sum,T[x].sum %= Mod;
	return ;
}
inline int read();
signed main(){
	//freopen("1.in","r",stdin);
	//freopen("1.out","w",stdout);
	cin >> n >> m >> Mod;
	for(int i = 1 ; i <= n ; i ++)
		a[i] = read();
	//cin >> m;
	build_tree(1,1,n);
	int tot = 0;
	for(int v = 1 ; v <= m ;v ++){
		int op,x,y,z;
		op = read();
		if(op == 1 || op == 2){
			x = read() , y = read() , z = read();
			z %= Mod;
			change(1,x,y,z,op);
		}
		else {
			x = read(),y = read(),
			cout << get(1,x,y) % Mod<< endl,
			tot ++;
		}
	}
	return 0;
}
inline int read(){
	int x = 0 ,flag = 1;
	char ch = getchar();
	for( ; ch > '9' || ch < '0' ; ch = getchar())if(ch == '-')flag = -1;
	for( ; ch >= '0' && ch <= '9' ; ch = getchar())x = (x << 3) + (x << 1) + ch - '0';
	return x*flag;
}

线段树模板2,支持区间乘法,区间加法,区间求和,70分Wa三个当n = 100000的情况的点,求助!

2020/10/15 11:55
加载中...