社区讨论

开了long long 还是只有70分 求调

P3373【模板】线段树 2参与者 1已保存回复 0

讨论操作

快速查看讨论及其快照的属性,并进行相关操作。

当前回复
0 条
当前快照
1 份
快照标识符
@ltya5s91
此快照首次捕获于
2024/03/19 19:17
2 年前
此快照最后确认于
2024/03/19 20:51
2 年前
查看原帖
CPP

#include <iostream>
#define N 100005
#define ll long long
using namespace std;
ll n, q, m;
ll a[N];
struct node
{
	ll l, r;
	ll add, mul;
	ll sum;
}tree[N*4];

void build(ll i, ll l, ll r)
{
	tree[i].l = l;
	tree[i].r = r;
	tree[i].mul = 1;
	if (l == r)
	{
		tree[i].sum = a[l];//注意这里是a[l]或者a[r]   不是a[i]!!!!!
		return;
	}
	ll mid = (l + r) / 2;
	build(i * 2, l, mid);
	build(i * 2 + 1, mid + 1, r);
	tree[i].sum = (tree[i * 2].sum + tree[i * 2 + 1].sum) % m;
}

void down(ll i)
{
	tree[i * 2].add = (tree[i * 2].add * tree[i].mul + tree[i].add) % m;
	tree[i * 2].mul = (tree[i * 2].mul * tree[i].mul) % m;
	tree[i * 2].sum = (tree[i * 2].sum * tree[i].mul + (tree[i * 2].r - tree[i * 2].l + 1) * tree[i].add) % m;

	tree[i * 2 + 1].add = (tree[i * 2 + 1].add * tree[i].mul + tree[i].add) % m;
	tree[i * 2 + 1].mul = (tree[i * 2 + 1].mul * tree[i].mul) % m;
	tree[i * 2 + 1].sum = (tree[i * 2 + 1].sum * tree[i].mul + (tree[i * 2 + 1].r - tree[i * 2 + 1].l + 1) * tree[i].add) % m;

	tree[i].add = 0;
	tree[i].mul = 1;
}
void upd_add(ll i, ll l, ll r, ll k)
{
	if (tree[i].r < l || tree[i].l > r)
		return;
	if (tree[i].l >= l && tree[i].r <= r)
	{
		tree[i].add = (tree[i].add + k) % m;
		tree[i].sum = (tree[i].sum + (tree[i].r - tree[i].l + 1) * k) % m;
		return;
	}
	if (tree[i].add > 0 || tree[i].mul > 1)
		down(i);
	upd_add(i * 2, l, r, k);
	upd_add(i * 2 + 1, l, r, k);
	tree[i].sum = (tree[i * 2].sum + tree[i * 2 + 1].sum) % m;
}
void upd_mul(ll i, ll l, ll r, ll k)
{
	if (tree[i].r < l || tree[i].l > r)
		return;
	if (tree[i].l >= l && tree[i].r <= r)
	{
		tree[i].add = (tree[i].add * k) % m;
		tree[i].mul = (tree[i].mul * k) % m;
		tree[i].sum = (tree[i].sum * k) % m;
		return;
	}
	down(i);
	upd_mul(i * 2, l, r, k);
	upd_mul(i * 2 + 1, l, r, k);
	tree[i].sum = (tree[i * 2].sum + tree[i * 2 + 1].sum) % m;
}
ll query(ll i, ll l, ll r)
{
	if (tree[i].l > r || tree[i].r < l)
		return 0;
	if (tree[i].l >= l && tree[i].r <= r)
		return tree[i].sum;
	if (tree[i].add > 0 || tree[i].mul > 1)
		down(i);
	return (query(i * 2, l, r) + query(i * 2 + 1, l, r))%m;

}
int main()
{
	cin >> n >> q>>m;
	for (ll i = 1; i <= n; i++)
		cin >> a[i];
	build(1, 1, n);
	for (ll i = 1; i <= q; i++)
	{
		ll p, x, y, k;
		cin >> p >> x >> y;
		if (p == 1)
		{
			cin >> k;
			upd_mul(1, x, y, k);
		}
		else if (p == 2)
		{
			cin >> k;
			upd_add(1, x, y, k);
		}
		else
		{
			cout << query(1, x, y) << endl;
		}
	}
	return 0;
}

回复

0 条回复,欢迎继续交流。

正在加载回复...