Submission #1076747

#TimeUsernameProblemLanguageResultExecution timeMemory
1076747Yang8onConstruction of Highway (JOI18_construction)C++17
100 / 100
211 ms19800 KiB
#include <bits/stdc++.h>
#define Y8o "Construction of Highway"
#define maxn (int) 1e5 + 5
#define ll long long
#define pii pair<int, int>
#define gb(i, j) ((i >> j) & 1)
#define all(x) x.begin(), x.end()
#define _left id * 2, l, mid
#define _right id * 2 + 1, mid + 1, r

#define f first
#define s second

using namespace std;

mt19937_64 rng(chrono::steady_clock::now().time_since_epoch().count());
ll GetRandom(ll l, ll r) {
    return uniform_int_distribution<ll> (l, r) (rng);
}
void iof() {
    if(fopen(Y8o".inp", "r"))
    {
        freopen(Y8o".inp", "r", stdin);
//        freopen(Y8o".out", "w", stdout);
    }
    ios_base::sync_with_stdio(0);
    cin.tie(NULL), cout.tie(NULL);
}
void ctime() {
    cerr << "\n" << "\nTime elapsed: " << 1000 * clock() / CLOCKS_PER_SEC << "ms\n";
}


int n, a[maxn];
pii ed[maxn];
vector<int> cur, o[maxn];
int sz[maxn], h[maxn], par[maxn];
ll ans;

void dfs(int u = 1, int p = 0) {
    sz[u] = 1;
    for(int v : o[u]) if(v != p) {
        par[v] = u, h[v] = h[u] + 1;
        dfs(v, u);
        sz[u] += sz[v];
    }
}

int chain;
int chainIn[maxn], chainHead[maxn];
void hld(int u = 1, int p = 0) {
    if(!chainHead[chain]) chainHead[chain] = u;
    chainIn[u] = chain;
    int mxchild = -1;
    for(int v : o[u]) if(v != p) {
        if(mxchild == -1 || sz[v] > sz[mxchild]) mxchild = v;
    }
    if(mxchild != -1) hld(mxchild, u);
    for(int v : o[u]) if(v != p && v != mxchild) {
        chain ++, hld(v, u);
    }
}

struct BIT {
    int bit[maxn];

    void update(int x, int val) {
        while(x <= n) bit[x] += val, x += (x & -x);
    }
    int get(int x, int best = 0) {
        while(x) best += bit[x], x -= (x & -x);
        return best;
    }
} B;

vector<pii> child[maxn]; /// f -> node, s -> cl
void prog(int p, int u, int val, vector<pii>& st) {
    vector<pii> tmp; /// f -> cl, s -> sl
    int pre = h[p] - 1;
    while(child[p].size() && h[child[p].back().f] < h[u]) {
        tmp.push_back({ child[p].back().s, h[child[p].back().f] - pre });
        pre = h[child[p].back().f];
        child[p].pop_back();
    }
    if(child[p].size()) tmp.push_back({ child[p].back().s, h[u] - pre });
    child[p].push_back({ u, val });

    reverse(all(tmp));
    for(auto x : tmp) st.push_back(x);
}
int cntqer = 0;
void Upd(int u, int val) {
    cntqer ++;
    vector<pii> st; /// f -> cl, s -> sl
    while(1) {
        if(chainIn[u] == chainIn[1]) {
            prog(1, u, val, st);
            break;
        }
        prog(chainHead[chainIn[u]], u, val, st);
        u = par[chainHead[chainIn[u]]];
    }

    for(auto [cl, sl] : st) ans += 1ll * sl * B.get(cl), B.update(cl + 1, +sl);
    for(auto [cl, sl] : st) B.update(cl + 1, -sl);
}

void solve() {
    cin >> n ;
    for(int i = 1; i <= n; i ++) cin >> a[i], cur.push_back( a[i] );

    sort( all(cur) );
    cur.resize( unique(all(cur)) - cur.begin() );
    for(int i = 1; i <= n; i ++) a[i] = lower_bound(all(cur), a[i]) - cur.begin() + 1;

    for(int i = 1; i <= n - 1; i ++) {
        int u, v; cin >> u >> v;
        o[u].push_back(v), o[v].push_back(u);
        ed[i] = {u, v};
    }

    dfs(), hld();
    Upd(1, a[1]);

    for(int i = 1; i <= n - 1; i ++) {
        int u, v; tie(u, v) = ed[i];
        ans = 0, Upd(v, a[v]);
        cout << ans << '\n';
    }
}


int main() {
    iof();

    int nTest = 1;
//    cin >> nTest;

    while(nTest --) {
        solve();
    }

    ctime();
    return 0;
}

Compilation message (stderr)

construction.cpp: In function 'void iof()':
construction.cpp:23:16: warning: ignoring return value of 'FILE* freopen(const char*, const char*, FILE*)' declared with attribute 'warn_unused_result' [-Wunused-result]
   23 |         freopen(Y8o".inp", "r", stdin);
      |         ~~~~~~~^~~~~~~~~~~~~~~~~~~~~~~
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...