Submission #1245630

#TimeUsernameProblemLanguageResultExecution timeMemory
1245630BoomydayTree (IOI24_tree)C++20
41 / 100
138 ms66248 KiB
#include <bits/stdc++.h> #include "tree.h" using namespace std; using ll = long long; const ll INF = 1'000'000'000'000'000'000LL; const ll ssz = 524288; ll n; vector<ll> p, w; vector<vector<ll>> adj; vector<bool> is_leaf; vector<ll> LL, RR; vector<pair<ll, ll>> special_pairs; ll T = 0; ll leaf_sum = 0; vector<ll> seg_leaf(2 * ssz, 0); vector<pair<ll, ll>> seg_weight(2 * ssz, {INF, -1}); vector<ll> Rx, Lx; void add_leaf(ll i, ll x) { i += ssz; seg_leaf[i] = x; for (i /= 2; i > 0; i /= 2) seg_leaf[i] = seg_leaf[2 * i] + seg_leaf[2 * i + 1]; } ll sum_leaf(ll l, ll r) { l += ssz; r += ssz; ll ans = 0; while (l <= r) { if (l % 2 == 1) ans += seg_leaf[l++]; if (r % 2 == 0) ans += seg_leaf[r--]; l /= 2; r /= 2; } return ans; } void upd_weight(ll i, pair<ll, ll> x) { i += ssz; seg_weight[i] = x; for (i /= 2; i > 0; i /= 2) seg_weight[i] = min(seg_weight[2 * i], seg_weight[2 * i + 1]); } pair<ll, ll> min_val(ll l, ll r) { l += ssz; r += ssz; pair<ll, ll> ans = {INF, -1}; while (l <= r) { if (l % 2 == 1) ans = min(ans, seg_weight[l++]); if (r % 2 == 0) ans = min(ans, seg_weight[r--]); l /= 2; r /= 2; } return ans; } void dfs1(ll u) { is_leaf[u] = true; LL[u] = T++; for (ll v : adj[u]) { is_leaf[u] = false; dfs1(v); } if (is_leaf[u]) { leaf_sum += w[u]; w[u] = INF; } RR[u] = T - 1; } void dfs(ll u, ll sub) { if (is_leaf[u]) { is_leaf[u] = false; add_leaf(LL[u], 0); return; } auto [min_weight, index] = min_val(LL[u], RR[u]); special_pairs.push_back({min_weight - sub, sum_leaf(LL[u], RR[u])}); sub = min_weight; for (ll v : adj[index]) dfs(v, sub); is_leaf[index] = true; add_leaf(LL[index], 1); upd_weight(LL[index], {INF, index}); w[index] = INF; dfs(u, sub); } void init(vector<signed> P, vector<signed> W) { n = P.size(); p.resize(n); w.resize(n); for (ll i = 0; i < n; ++i) { p[i] = P[i]; w[i] = W[i]; } adj.assign(n, {}); for (ll i = 1; i < n; ++i) adj[p[i]].push_back(i); is_leaf.assign(n, false); LL.assign(n, 0); RR.assign(n, 0); T = 0; leaf_sum = 0; dfs1(0); for (ll i = 0; i < n; i++) { if (is_leaf[i]) add_leaf(LL[i], 1); upd_weight(LL[i], {w[i], i}); } dfs(0, 0); Rx.assign(n + 1, 0); Lx.assign(n + 1, 0); Lx[0] = leaf_sum; for (auto& [wt, c] : special_pairs) { Lx[1] += c * wt; Lx[c + 1] -= c * wt; Rx[1] -= wt; Rx[c + 1] += wt; } for (ll i = 1; i <= n; ++i) { Lx[i] += Lx[i - 1]; Rx[i] += Rx[i - 1]; } } ll query(signed L, signed R) { if (L == 0) return 0; ll k = (R + L - 1) / L; return L * Lx[k] + R * Rx[k]; }
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...