QOJ.ac

QOJ

ID题目提交者结果用时内存语言文件大小提交时间测评时间
#40170#2831. Game TheoryDoIdoWA 80ms55616kbC++236.2kb2022-07-16 20:45:552022-07-16 20:45:56

Judging History

你现在查看的是最新测评结果

  • [2023-08-10 23:21:45]
  • System Update: QOJ starts to keep a history of the judgings of all the submissions.
  • [2022-07-16 20:45:56]
  • 评测
  • 测评结果:WA
  • 用时:80ms
  • 内存:55616kb
  • [2022-07-16 20:45:55]
  • 提交

answer

#include <bits/stdc++.h>
using namespace std;
typedef long long ll;

#pragma region Debug
template<typename T>
std::istream& operator>> (std::istream& in, std::vector<T>& v)
{
	for (auto& val : v) {
		in >> val;
	}
	return in;
}
template<typename T>
std::ostream& operator<< (std::ostream& out, const std::vector<T>& v)
{
	for (const auto& val : v) {
		out << val << ' ';
	}
	return out;
}

void debugAll() {  }
template<typename T1, typename... T2>
void debugAll(const T1& first, const T2&... second)
{
	std::cout << first;
	if (sizeof...(second)) {
		std::cout << ", ";
	}
	debugAll(second...);
}
template<typename T1, typename... T2>
void debug(const T1& first, const T2&... second)
{
	std::cout << "[";
	debugAll(first, second...);
	std::cout << "]" << std::endl;
}
template<typename T>
void debug(const std::vector<T>& v) {
	std::cout << '[';
	for (int i = 0; i < v.size(); i++) {
		std::cout << v[i];
		if (i < v.size() - 1) cout << ", ";
	}
	std::cout << ']' << std::endl;
}
#pragma endregion

#define Debug
#ifdef Debug
#else
#define debug(...)
#endif
#define N (int)(2e5 + 10)
#define MOD (int)(998244353)

struct Node {
	int l, r;
	int cnt0;
	int cnt1;
	ll pre0, pre1;
	ll suf0, suf1;
	bool flag;
	int last0, last1;

	Node() {
		l = 0, r = 0;
		cnt0 = 0, cnt1 = 0;
		pre0 = 0, pre1 = 0;
		suf0 = 0, suf1 = 0;
		flag = false;
		last0 = last1 = 0;
	}
	Node(const int val, const int l, const int r)
	{
		this->l = 0;
		this->r = 0;
		cnt0 = 0, cnt1 = 0;
		pre0 = 0, pre1 = 0;
		suf0 = 0, suf1 = 0;
		flag = false;
		last0 = last1 = 0;

		this->l = l;
		this->r = r;
		if (val == 0) cnt0 = 1;
		if (val == 1) cnt1 = 1;
	}
	void init(int l, int r, int val = -1)
	{
		pre0 = 0, pre1 = 0;
		suf0 = 0, suf1 = 0;
		flag = false;
		last0 = last1 = 0;

		this->l = l;
		this->r = r;
		if (val == 0) cnt0 = 1, last0 = l;
		if (val == 1) cnt1 = 1, last1 = l;
	}
	void clear()
	{
		l = 0, r = 0;
		cnt0 = 0;
		cnt1 = 0;
		pre0 = 0, pre1 = 0;
		suf0 = 0, suf1 = 0;
		flag = false;
		last0 = 0, last1 = 0;
	}
	int len() const
	{
		return r - l + 1;
	}
	void pushup(const Node& A, const Node& B)
	{
		cnt0 = A.cnt0 + B.cnt0;
		cnt1 = A.cnt1 + B.cnt1;
		pre0 = A.pre0 + B.pre0 + (1LL * B.cnt0 * A.len());
		pre1 = A.pre1 + B.pre1 + (1LL * B.cnt1 * A.len());
		suf0 = B.suf0 + A.suf0 + (1LL * A.cnt0 * B.len());
		suf1 = B.suf1 + A.suf1 + (1LL * A.cnt1 * B.len());
		pre0 %= MOD;
		pre1 %= MOD;
		suf0 %= MOD;
		suf1 %= MOD;
		if (B.last0) last0 = B.last0;
		else last0 = A.last0;
		if (B.last1) last1 = B.last1;
		else last1 = A.last1;
	}
};
void debug(const Node& A)
{
	printf("l = %d, r = %d\n", A.l, A.r);
	printf("cnt0 = %d, cnt1 = %d\n", A.cnt0, A.cnt1);
	printf("pre0 = %lld, pre1 = %lld\n", A.pre0, A.pre1);
	printf("suf0 = %lld, suf1 = %lld\n", A.suf0, A.suf1);

}

Node tr[N * 4];

struct SegmentTree {
public:
	const int n;

private:
	inline void __pushup(int u)
	{
		tr[u].pushup(tr[u << 1], tr[u << 1 | 1]);
		//tr[u] = tr[u << 1] + tr[u << 1 | 1];
	}
	inline void __pushdown(int u)
	{
		if (tr[u].flag) {
			__modify(tr[u << 1]);
			__modify(tr[u << 1 | 1]);
			tr[u].flag = false;
		}
	}
	inline void __modify(Node& node)
	{
		node.flag = !node.flag;
		swap(node.cnt0, node.cnt1);
		swap(node.pre0, node.pre1);
		swap(node.suf0, node.suf1);
		swap(node.last0, node.last1);
	}

public:
	inline SegmentTree(const int& n, int* init) : n(n)
	{
		__build(1, 1, n, init);
	}
	inline void __build(int u, int l, int r, int* init)
	{
		if (l == r) {
			tr[u].init(l, r, init[l]);
			return;
		}

		tr[u].init(l, r);
		int mid = (l + r) >> 1;
		__build(u << 1, l, mid, init);
		__build(u << 1 | 1, mid + 1, r, init);
		__pushup(u);
	}
	inline void modify(int u, int l, int r) {
		if (tr[u].l >= l && tr[u].r <= r) {
			__modify(tr[u]);
			return;
		}

		__pushdown(u);
		int mid = (tr[u].l + tr[u].r) >> 1;
		if (l <= mid) modify(u << 1, l, r);
		if (r >= mid + 1) modify(u << 1 | 1, l, r);
		__pushup(u);
	}
	inline void modify(int l, int r) {
		modify(1, l, r);
	}
	inline Node query(int u, int l, int r, int ql, int qr) {
		if (ql > qr) return Node();
		if (l >= ql && r <= qr) {
			return tr[u];
		}

		__pushdown(u);
		int mid = (l + r) >> 1;
		if (qr <= mid) return query(u << 1, l, mid, ql, qr);
		if (ql >= mid + 1) return query(u << 1 | 1, mid + 1, r, ql, qr);

		Node res;
		res.pushup(
			query(u << 1, l, mid, ql, qr),
			query(u << 1 | 1, mid + 1, r, ql, qr)
		);
		return res;
	}
	inline Node query(int l, int r) {
		return query(1, 1, n, l, r);
	}
	/*void debug(int u, int l, int r) {
		if (l == r) {
			return;
		}

		int mid = (l + r) >> 1;
		debug(u << 1, l, mid);
		debug(u << 1 | 1, mid + 1, r);
	}*/
	void clear()
	{
		for (int i = 1; i <= n * 4; i++) {
			tr[i].clear();
		}
	}
};

int n, q;
char str[N];
int bit[N * 10];

int main()
{
	while (scanf("%d %d", &n, &q) != EOF) {
		scanf("%s", str + 1);
		for (int i = 1; i <= n; i++) {
			bit[i] = str[i] - '0';
		}

		SegmentTree seg(n, bit);
		/*Node t1 = seg.query(1, n);
		debug(t1);
		Node t2 = seg.query(n, n);
		debug(t2);*/

		for (int i = 1; i <= q; i++) {
			int l, r;
			scanf("%d %d", &l, &r);
			seg.modify(l, r);
			//while (true);

			// 总的
			Node t = seg.query(1, n);
			int last = t.last1;

			int pos = t.cnt1;
			//debug(pos);
			if (pos == 0) {
				printf("0\n");
				continue;
			}

			Node tk = seg.query(pos, pos);
			bool val = false;
			if (tk.cnt1) val = true;
			Node left = seg.query(1, pos - 1);
			Node right = seg.query(pos + 1, last);

			if (left.cnt1 == t.cnt1) {
				printf("%lld\n", left.cnt1);
				continue;
			}

			ll cnt = left.cnt0 + right.cnt1;
			ll ans = (cnt + 1) * last % MOD;
			ll sub = left.pre0 + right.suf1;
			sub *= 2;
			sub %= MOD;
			ans -= sub;
			ans = (ans % MOD + MOD) % MOD;
			ans -= cnt;
			ans = (ans % MOD + MOD) % MOD;
			if (val) ans -= last - pos;
			else ans -= pos - 1;
			ans = (ans % MOD + MOD) % MOD;

			printf("%lld\n", ans);
			//cout << ans << endl;
		}
		seg.clear();
	}
	return 0;
}

/*
3 2
010
1 2
2 3
5 1
00000
1 5

11 20
00010111000

11101011000

*/

详细

Test #1:

score: 100
Accepted
time: 4ms
memory: 55616kb

input:

3 2
010
1 2
2 3
5 1
00000
1 5

output:

1
3
5

result:

ok 3 lines

Test #2:

score: 0
Accepted
time: 0ms
memory: 54048kb

input:

1 1
0
1 1

output:

1

result:

ok single line: '1'

Test #3:

score: 0
Accepted
time: 61ms
memory: 54448kb

input:

2 2
01
2 2
2 2
2 2
01
1 2
1 2
1 2
1
1 1
1 1
1 2
1
1 1
1 1
2 2
00
1 2
1 2
2 2
11
1 2
1 2
2 2
01
2 2
1 1
2 2
10
2 2
1 2
2 2
01
1 2
1 2
1 2
0
1 1
1 1
2 2
01
1 2
2 2
1 2
0
1 1
1 1
1 2
1
1 1
1 1
2 2
10
1 2
1 1
1 2
0
1 1
1 1
2 2
01
1 2
1 2
2 2
10
1 2
1 1
1 2
0
1 1
1 1
1 2
0
1 1
1 1
1 2
1
1 1
1 1
2 2
10
1 ...

output:

0
3
1
3
0
1
0
1
2
0
0
2
0
1
2
0
1
3
1
0
1
2
1
0
0
1
3
2
1
0
1
3
3
2
1
0
1
0
0
1
0
1
0
2
2
1
0
1
2
1
1
0
2
0
2
3
1
0
0
1
2
0
0
1
0
1
0
1
1
0
1
2
2
0
0
2
0
1
0
1
1
0
1
0
1
0
0
1
0
1
0
1
2
0
3
0
1
0
0
1
1
0
1
0
1
2
0
2
1
0
0
3
1
2
0
1
3
2
1
0
0
1
2
0
2
0
0
1
0
1
1
0
1
0
1
0
1
0
1
2
1
0
3
1
0
3
0
1
0
1
...

result:

ok 200000 lines

Test #4:

score: -100
Wrong Answer
time: 80ms
memory: 53844kb

input:

11 20
00010111000
1 6
1 11
5 6
8 11
1 4
3 8
4 11
1 7
5 9
1 4
6 10
5 6
1 7
5 10
1 10
9 11
6 8
1 4
8 11
1 4
10 20
0101000010
3 4
2 2
4 8
4 6
6 7
3 7
3 3
1 5
1 5
6 8
2 2
2 4
2 6
5 7
1 3
2 5
6 8
7 9
5 8
3 10
4 20
1011
2 4
1 4
1 3
2 3
1 1
2 2
1 2
2 4
1 2
3 4
3 4
3 4
1 4
2 2
1 4
1 3
1 1
1 3
1 3
2 2
4 20
1...

output:

16
55
53
25
13
15
43
52
41
33
34
40
43
45
35
28
25
33
45
37
19
26
35
38
36
41
36
29
36
29
22
37
20
23
28
20
21
10
14
30
2
10
5
7
10
9
7
2
0
10
0
10
2
1
9
6
7
4
7
8
4
9
1
6
8
3
5
7
3
7
6
8
6
9
6
7
2
0
5
3
66
105
83
68
92
149
116
100
109
116
139
120
119
104
124
77
94
88
61
53
40
51
25
21
32
59
67
32
2...

result:

wrong answer 22nd lines differ - expected: '20', found: '26'