分块 WA 20pts 求调
查看原帖
分块 WA 20pts 求调
860817
Starstream楼主2024/1/10 09:26
#include <iostream>
#include <cmath>
#include <algorithm>
#define int long long

using namespace std;

const int N = 1000010, M = 1010;

int n, m;
int w[N];
int L[M], R[M];
int id[N], add[M];

inline int find(int l, int r, int x)
{
	return lower_bound(w + l, w + r + 1, x) - (w);
}

inline void modify(int l, int r, int x)
{
	int p = id[l], q = id[r];
	if (p == q)
	{
		for (int i = l; i <= r; i ++ ) w[i] += x;
		sort(w + L[p], w + R[p] + 1);
		return;
	}
	if (p + 1 <= q - 1)
		for (int i = p + 1; i <= q - 1; i ++ )
			add[i] += x;
	for (int i = l; i <= R[p]; i ++ ) w[i] += x;
	for (int i = L[q]; i <= r; i ++ ) w[i] += x;
	sort(w + L[p], w + R[p] + 1), sort(w + L[q], w + R[q] + 1);
}

inline int query(int l, int r, int x)
{
	int p = id[l], q = id[r];
	if (p == q)
	{
		int res = 0;
		for (int i = l; i <= r; i ++ )
			if (w[i] + add[p] >= x) res ++ ;
		return res;
	}
	int res = 0;
	if (p + 1 <= q - 1)
		for (int i = p + 1; i <= q - 1; i ++ )
		{
			// int cnt = 0;
			// for (int j = L[i]; j <= R[i]; j ++ ) if (x <= w[j] + add[i]) cnt ++ ;
			// cout << cnt << endl;
			// cout << (R[i] - L[i] + 1) - (find(L[i], R[i] + 1, x - add[i]) - 1) << endl;
			res += (R[i] - find(L[i], R[i], x - add[i]) + 1);
		}
	for (int i = l; i <= R[p]; i ++ )
		if (w[i] + add[p] >= x) res ++ ;
	for (int i = L[q]; i <= r; i ++ )
		if (w[i] + add[q] >= x) res ++ ;
	return res;
}

signed main()
{
	scanf("%lld%lld", &n, &m);
	for (int i = 1; i <= n; i ++ )
		scanf("%lld", &w[i]);

	int len = max(1ll, (int)sqrt(n));
	for (int i = 1; i <= len; i ++ )
		L[i] = (i - 1) * len + 1, R[i] = i * len;
	if (R[len] < n) R[len] = n;
	for (int i = 1; i <= len; i ++ )
		for (int j = L[i]; j <= R[i]; j ++ )
			id[j] = i;

	char op[3]; int l, r, x;
	while (m -- )
	{
		scanf("%s%lld%lld%lld", op, &l, &r, &x);
		if (*op == 'M') modify(l, r, x);
		else printf("%lld\n", query(l, r, x));
	}
	return 0;
}
2024/1/10 09:26
加载中...