分块求助
查看原帖
分块求助
333478
memset_0x3f楼主2022/3/22 21:04

RT,分块暴力,2、9、10点一直会超时,加上快读反而更慢,不知道是我快读写假了还是咋的。。。

#include <bits/stdc++.h>

using namespace std;

#define ll long long
#define int long long

const int N = 1e5 + 5;

int n, m, p, block, id[N];
ll a[N], s[N], add[N], mul[N];

void push_down(int k) {
	for (int i = (k - 1) * block + 1; i <= k * block; ++i)
		a[i] = (a[i] * mul[k] + add[k] + p) % p;
	mul[k] = 1, add[k] = 0;
	return ;
}

void modify_add(int l, int r, int c) {
	int ld = id[l], rd = id[r];
	push_down(ld);
	if (ld == rd) {
		for (int i = l; i <= r; ++i) {
			a[i] = (a[i] + c + p) % p;
			s[ld] = (s[ld] + c + p) % p;
		}
		return ;
	}
	push_down(rd);
	for (int i = l; id[i] == ld; ++i) {
		a[i] = (a[i] + c + p) % p;
		s[ld] = (s[ld] + c + p) % p;
	}
	for (int i = ld + 1; i < rd; ++i) {
		add[i] = (add[i] + c + p) % p;
		s[i] = (s[i] + c * block + p) % p;
	}
	for (int i = r; id[i] == rd; --i) {
		a[i] = (a[i] + c + p) % p;
		s[rd] = (s[rd] + c + p) % p;
	}
	return ;
}

void modify_mul(int l, int r, int c) {
	int ld = id[l], rd = id[r];
	push_down(ld);
	if (ld == rd) {
		for (int i = l; i <= r; ++i) {
			s[ld] = (s[ld] + a[i] * (c - 1)  + p) % p;
			a[i] = (a[i] * c + p) % p;
		}
		return ;
	}
	push_down(rd);
	for (int i = l; id[i] == ld; ++i) {
		s[ld] = (s[ld] + a[i] * (c - 1) + p) % p;
		a[i] = (a[i] * c + p) % p;
	}
	for (int i = ld + 1; i < rd; ++i) {
		mul[i] = (mul[i] * c + p) % p;
		s[i] = (s[i] * c + p) % p;
		add[i] = (add[i] + p) * c % p;
	}
	for (int i = r; id[i] == rd; --i) {
		s[rd] = (s[rd] + a[i] * (c - 1) + p) % p;
		a[i] = (a[i] * c + p) % p;
	}
	return ;
}

ll query(int l, int r) {
	int ld = id[l], rd = id[r];
	ll ans = 0;
	if (ld == rd) {
		for (int i = l; i <= r; ++i)
			ans = (ans + a[i] * mul[ld] + add[ld] + p) % p;
		return ans;
	}
	for (int i = l; id[i] == ld; ++i)
		ans = (ans + a[i] * mul[ld] + add[ld] + p) % p;
	for (int i = ld + 1; i < rd; ++i)
		ans = (ans + s[i] + p) % p;
	for (int i = r; id[i] == rd; --i)
		ans = (ans + a[i] * mul[rd] + add[rd] + p) % p;
	return ans;
}

signed main() {
	ios::sync_with_stdio(false); cin.tie(0);
	cin >> n >> m >> p;
	block = sqrt(n);
	for (int i = 1; i <= n; ++i) {
		cin >> a[i];
		id[i] = (i - 1) / block + 1;
		s[id[i]] += a[i];
		mul[i] = 1;
	}
	for (int i = 1; i <= m; ++i) {
		int opt, x, y, k;
		cin >> opt;
		if (opt == 1) {
			cin >> x >> y >> k;
			modify_mul(x, y, k);
		}
		else if (opt == 2) {
			cin >> x >> y >> k;
			modify_add(x, y, k);
		}
		else {
			cin >> x >> y;
			cout << query(x, y) << '\n';
		}
	}
	return 0;
}
2022/3/22 21:04
加载中...