Submission #1367162

#TimeUsernameProblemLanguageResultExecution timeMemory
1367162lanternerRegions (IOI09_regions)C++20
100 / 100
3282 ms121476 KiB
#include <bits/stdc++.h>
#define ll long long
#define ii pair<ll, ll>
#define ff first
#define ss second
#define pb(x) push_back(x)
#define vii vector<ll>
#define ump unordered_map
#define sz(a) (int)a.size()
#define getbit(i, j) ((i >> j) & 1)
#define addbit(i, j) (i | (1 << j))
#define TIME (1.0 * clock() / CLOCKS_PER_SEC)
#define fto(i, a, b, x) for (int i = a; i <= b; i += x)
#define fdto(i, a, b, x) for (int i = a; i >= b; i -= x)
#define all(x) x.begin(), x.end()

using namespace std;
const ll maxN = 2e5+5;
const int maxR = 25005;
const int B = 500;

int n, R, Q, tin[maxN], tout[maxN], m;
int a[maxN];
vector<int> dothi[maxN], pos[maxR];
int heavycol[maxN];
ll cal1[505][maxR], cal2[maxR][505];
vector<int> v;

struct fenwick {
    int ft[maxN];

    void update (int i, int val) {
        for (; i <= n; i += i&-i) ft[i] += val;
    }

    int getval (int i) {
        int ans = 0;
        for (; i; i -= i&-i) ans += ft[i];
        return ans;
    }
};

fenwick ft[2];

void dfs (int u) {
    m++;
    tin[u] = m;
    for (int v : dothi[u]) {
        dfs(v);
    }
    tout[u] = m;
}

signed main() {
    ios::sync_with_stdio(false);
    cin.tie(0);
    cout.tie(0);
    cin >> n >> R >> Q;
    fto (i, 1, n, 1) {
    	int S, h; cin >> S;
    	if (i == 1) a[i] = S;
    	else {
    		cin >> h;
    		dothi[S].emplace_back(i);
    		a[i] = h;
    	}
    }
    dfs(1);
    fto (i, 1, n, 1) pos[a[i]].emplace_back(i);
    fto (i, 1, R, 1) {
        if (pos[i].size() > B) v.emplace_back(i);
    }
    //cerr << v.size() << '\n';
    fto (i, 0, sz(v)-1, 1) {
        heavycol[v[i]] = i;
        //cout << pos[v[i]].size() << ' ' << v[i] << '\n';
        for (int u : pos[v[i]]) {
            ft[0].update(tin[u], 1);
            ft[0].update(tout[u]+1, -1);
            ft[1].update(tin[u], 1);
        }
        fto (j, 1, R, 1) {
            for (int u : pos[j]) {
                //if (i == 0 && j == 3) cout << ft[0].getval(tin[u]) << ' ';
                cal1[i][j] += ft[0].getval(tin[u]);
                cal2[j][i] += ft[1].getval(tout[u]) - ft[1].getval(tin[u]-1);
            }
        }
        for (int u : pos[v[i]]) {
            ft[0].update(tin[u], -1);
            ft[0].update(tout[u]+1, 1);
            ft[1].update(tin[u], -1);
        }
    }
    while (Q--) {
        int u, v; cin >> u >> v;
        //cin.flush();
        if (pos[u].size() <= B && pos[v].size() <= B) {
            ll ans = 0;
            for (int k : pos[v]) ft[0].update(tin[k], 1);
            for (int k : pos[u]) ans += ft[0].getval(tout[k]) - ft[0].getval(tin[k]-1);
            for (int k : pos[v]) ft[0].update(tin[k], -1);
            cout << ans << endl;
        }
        else {
            if (pos[u].size() > B) {
                cout << cal1[heavycol[u]][v] << endl;
            }
            else {
                cout << cal2[u][heavycol[v]] << endl;
            }
        }
    }
    return 0;
}
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...