This submission is migrated from previous version of oj.uz, which used different machine for grading. This submission may have different result if resubmitted.
#include "circuit.h"
#include <vector>
#include <bits/stdc++.h>
using namespace std;
#define ll long long
#define pii pair<int, int>
#define pll pair<ll, ll>
#define ff first
#define ss second
#define pb push_back
const ll MOD = 1e9 + 2022;
const int mxN = 1e5 + 10;
vector<int> adj[2 * mxN];
int n, m;
bool state[2 * mxN];
ll contrib[2 * mxN];
void dfs1(int u = 0) {
if (u >= n) {
contrib[u] = 1; return;
}
contrib[u] = adj[u].size();
for (int v : adj[u]) {
dfs1(v);
contrib[u] = (contrib[u] * contrib[v]) % MOD;
}
}
void dfs2(int u = 0, ll pass = 1) {
if (u >= n) {
contrib[u] = pass; return;
}
int sz = adj[u].size();
vector<ll> pref(sz + 2), suff(sz + 2);
pref[0] = 1;
for (int i = 1; i <= sz; i++) {
pref[i] = (pref[i - 1] * contrib[adj[u][i - 1]]) % MOD;
}
suff[sz + 1] = 1;
for (int i = sz; i >= 1; i--) {
suff[i] = (suff[i + 1] * contrib[adj[u][i - 1]]) % MOD;
}
for (int i = 1; i <= sz; i++) {
ll nxt = pass;
nxt = (nxt * pref[i - 1]) % MOD;
nxt = (nxt * suff[i + 1]) % MOD;
dfs2(adj[u][i - 1], nxt);
}
}
ll seg[4 * mxN], tot[4 * mxN];
bool lazy[4 * mxN];
void pushdown(int idx) {
if (!lazy[idx]) return;
seg[(idx << 1)] = (tot[(idx << 1)] - seg[(idx << 1)] + MOD) % MOD;
seg[(idx << 1) | 1] = (tot[(idx << 1) | 1] - seg[(idx << 1) | 1] + MOD) % MOD;
lazy[(idx << 1)] ^= 1; lazy[(idx << 1) | 1] ^= 1;
lazy[idx] = false;
}
void build(int l = n, int r = n + m - 1, int idx = 1) {
if (l == r) {
seg[idx] = (state[l] ? contrib[l] : 0LL);
tot[idx] = contrib[l];
return;
}
int mid = (l + r) >> 1;
build(l, mid, (idx << 1));
build(mid + 1, r, (idx << 1) | 1);
seg[idx] = (seg[(idx << 1)] + seg[(idx << 1) | 1]) % MOD;
tot[idx] = (tot[(idx << 1)] + tot[(idx << 1) | 1]) % MOD;
}
void update(int tl, int tr, int l = n, int r = n + m - 1, int idx = 1) {
if (tl <= l && r <= tr) {
seg[idx] = (tot[idx] - seg[idx] + MOD) % MOD;
lazy[idx] ^= 1;
return;
}
pushdown(idx);
int mid = (l + r) >> 1;
if (tl <= mid) update(tl, tr, l, mid, (idx << 1));
if (tr > mid) update(tl, tr, mid + 1, r, (idx << 1) | 1);
seg[idx] = (seg[(idx << 1)] + seg[(idx << 1) | 1]) % MOD;
}
ll query() {
return seg[1];
}
void init(int N, int M, vector<int> P, vector<int> A) {
n = N; m = M;
for (int i = 1; i < (int)(P.size()); i++) adj[P[i]].pb(i);
for (int i = 0; i < (int)(A.size()); i++) state[n + i] = A[i];
dfs1(); dfs2();
build();
}
int count_ways(int L, int R) {
update(L, R);
return (int)(query());
}
/*
Observations:
Consider a particular source gate
Consider the set of solutions that toggles as the source gate toggles
(i.e. becomes valid/invalid as the source gate becomes on/off)
Then it can be shown that it is independent from other values
*/
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |