QOJ.ac
QOJ
ID | Problem | Submitter | Result | Time | Memory | Language | File size | Submit time | Judge time |
---|---|---|---|---|---|---|---|---|---|
#449426 | #8518. Roars III | luanmenglei | WA | 3ms | 16016kb | C++17 | 4.9kb | 2024-06-21 10:05:28 | 2024-06-21 10:05:29 |
Judging History
answer
#include <bits/stdc++.h>
using namespace std;
namespace SOL {
using i64 = long long;
void debug(const char *msg, ...) {
#ifdef CLESIP
va_list arg;
static char pbString[512];
va_start(arg,msg);
vsprintf(pbString,msg,arg);
cerr << "[DEBUG] " << pbString << "\n";
va_end(arg);
#endif
}
template<typename T, typename L>
bool chkmax(T &x, L y) { if (x < y) return x = y, true; return false; }
template<typename T, typename L>
bool chkmin(T &x, L y) { if (y < x) return x = y, true; return false; }
const int N = 2e5 + 10;
int n, dfn[N], id[N], sze[N], cnt;
i64 ans[N];
char str[N];
vector<int> adj[N];
const int SEG_SIZE = N * 4;
struct SegTree {
#define lc (x * 2)
#define rc (x * 2 + 1)
#define mid ((l + r) >> 1)
int tag[SEG_SIZE];
array<int, 2> cnt[SEG_SIZE], mx[SEG_SIZE];
i64 sum[SEG_SIZE];
void pull(int x) {
mx[x] = max(mx[lc], mx[rc]);
sum[x] = sum[lc] + sum[rc];
for (int op : { 0, 1 })
cnt[x][op] = cnt[lc][op] + cnt[rc][op];
}
void apply(int x, int k) {
tag[x] += k;
sum[x] += 1ll * k * (cnt[x][0] - cnt[x][1]);
mx[x][0] += k;
}
void push(int x) {
if (tag[x]) {
apply(lc, tag[x]);
apply(rc, tag[x]);
tag[x] = 0;
}
}
void set(int x, int l, int r, int p, int op, int k) {
if (l == r) {
cnt[x][op] = k;
if (cnt[x][1])
mx[x] = { tag[x], p };
else
mx[x] = { -1, 0 };
sum[x] = tag[x] * (cnt[x][0] - cnt[x][1]);
return;
}
push(x);
p <= mid ? set(lc, l, mid, p, op, k) : set(rc, mid + 1, r, p, op, k);
pull(x);
}
void add(int x, int l, int r, int ql, int qr, int k) {
if (ql > qr)
return;
if (ql <= l && r <= qr)
return apply(x, k);
push(x);
if (ql <= mid)
add(lc, l, mid, ql, qr, k);
if (mid < qr)
add(rc, mid + 1, r, ql, qr, k);
pull(x);
}
array<int, 2> query_max(int x, int l, int r, int ql, int qr) {
if (ql > qr)
return { -1, 0 };
if (ql <= l && r <= qr)
return mx[x];
push(x);
if (ql <= mid && mid < qr)
return max(query_max(lc, l, mid, ql, qr), query_max(rc, mid + 1, r, ql, qr));
else
return ql <= mid ? query_max(lc, l, mid, ql, qr) : query_max(rc, mid + 1, r, ql, qr);
}
void debug_print(int x, int l, int r) {
if (l == r) {
debug("pos: %d x: %d (%d, %d) dep: %d", l, id[l], cnt[x][0], cnt[x][1], tag[x]);
return;
}
push(x);
debug_print(lc, l, mid);
debug_print(rc, mid + 1, r);
}
#undef lc
#undef rc
#undef mid
} segt;
int pos[N];
void dfs1(int x, int p) {
dfn[x] = ++ cnt, id[dfn[x]] = x, sze[x] = 1;
for (int y : adj[x]) if (y != p) {
dfs1(y, x);
segt.add(1, 1, n, dfn[y], dfn[y] + sze[y] - 1, 1);
sze[x] += sze[y];
}
if (str[x] == '0') {
auto res = segt.query_max(1, 1, n, dfn[x], dfn[x] + sze[x] - 1);
if (res[1] != 0) {
pos[x] = id[res[1]];
segt.set(1, 1, n, dfn[pos[x]], 1, 0);
segt.set(1, 1, n, dfn[x], 1, 1);
}
} else {
segt.set(1, 1, n, dfn[x], 0, 1);
segt.set(1, 1, n, dfn[x], 1, 1);
}
}
void dfs2(int x, int p) {
// cerr << "visit " << x << "\n";
// segt.debug_print(1, 1, n);
ans[x] = segt.sum[1];
for (int y : adj[x]) if (y != p) {
int tmpx = 0, tmpy = 0;
if (pos[x]) {
segt.set(1, 1, n, dfn[x], 1, 0);
segt.set(1, 1, n, dfn[pos[x]], 1, 1);
}
if (pos[y]) {
segt.set(1, 1, n, dfn[y], 1, 0);
segt.set(1, 1, n, dfn[pos[y]], 1, 1);
}
segt.add(1, 1, n, dfn[y], dfn[y] + sze[y] - 1, -1);
segt.add(1, 1, n, 1, dfn[y] - 1, 1);
segt.add(1, 1, n, dfn[y] + sze[y], n, 1);
if (str[x] == '0') {
auto res = max(segt.query_max(1, 1, n, 1, dfn[y] - 1), segt.query_max(1, 1, n, dfn[y] + sze[y], n));
if (res[1] != 0) {
tmpx = id[res[1]];
segt.set(1, 1, n, dfn[tmpx], 1, 0);
segt.set(1, 1, n, dfn[x], 1, 1);
}
}
if (str[y] == '0') {
auto res = segt.mx[1];
if (res[1] != 0) {
tmpy = id[res[1]];
segt.set(1, 1, n, dfn[tmpy], 1, 0);
segt.set(1, 1, n, dfn[y], 1, 1);
}
}
swap(pos[x], tmpx);
swap(pos[y], tmpy);
dfs2(y, x);
swap(pos[x], tmpx);
swap(pos[y], tmpy);
if (tmpy) {
segt.set(1, 1, n, dfn[y], 1, 0);
segt.set(1, 1, n, dfn[tmpy], 1, 1);
}
if (tmpx) {
segt.set(1, 1, n, dfn[x], 1, 0);
segt.set(1, 1, n, dfn[tmpx], 1, 1);
}
segt.add(1, 1, n, dfn[y], dfn[y] + sze[y] - 1, 1);
segt.add(1, 1, n, 1, dfn[y] - 1, -1);
segt.add(1, 1, n, dfn[y] + sze[y], n, -1);
if (pos[y]) {
segt.set(1, 1, n, dfn[pos[y]], 1, 0);
segt.set(1, 1, n, dfn[y], 1, 1);
}
if (pos[x]) {
segt.set(1, 1, n, dfn[pos[x]], 1, 0);
segt.set(1, 1, n, dfn[x], 1, 1);
}
}
}
void solve() {
cin >> n >> (str + 1);
for (int i = 1, x, y; i < n; i ++) {
cin >> x >> y;
adj[x].push_back(y), adj[y].push_back(x);
}
dfs1(1, 0);
dfs2(1, 0);
for (int i = 1; i <= n; i ++)
cout << ans[i] << " \n"[i == n];
}
}
int main() {
ios::sync_with_stdio(false), cin.tie(0), cout.tie(0);
SOL::solve();
return 0;
}
Details
Tip: Click on the bar to expand more detailed information
Test #1:
score: 100
Accepted
time: 3ms
memory: 16016kb
input:
5 10101 1 2 2 3 2 4 4 5
output:
2 2 2 3 3
result:
ok 5 number(s): "2 2 2 3 3"
Test #2:
score: 0
Accepted
time: 2ms
memory: 9740kb
input:
1 0
output:
0
result:
ok 1 number(s): "0"
Test #3:
score: 0
Accepted
time: 0ms
memory: 15864kb
input:
1 1
output:
0
result:
ok 1 number(s): "0"
Test #4:
score: 0
Accepted
time: 0ms
memory: 11844kb
input:
2 10 1 2
output:
0 1
result:
ok 2 number(s): "0 1"
Test #5:
score: 0
Accepted
time: 1ms
memory: 11772kb
input:
3 100 2 3 2 1
output:
0 1 2
result:
ok 3 number(s): "0 1 2"
Test #6:
score: 0
Accepted
time: 2ms
memory: 11928kb
input:
4 1100 4 1 4 3 4 2
output:
1 1 3 1
result:
ok 4 number(s): "1 1 3 1"
Test #7:
score: -100
Wrong Answer
time: 0ms
memory: 11776kb
input:
5 10100 4 5 1 3 2 1 3 5
output:
0 0 0 0 0
result:
wrong answer 2nd numbers differ - expected: '2', found: '0'