제출 #1257833

#제출 시각아이디문제언어결과실행 시간메모리
1257833biank이주 (IOI25_migrations)C++20
30 / 100
83 ms1148 KiB
#include "migrations.h"
#include <bits/stdc++.h>

using namespace std;

#define forsn(i, s, n) for (int i = int(s); i < int(n); i++)
#define forn(i, n) forsn(i, 0, n)
#define dforsn(i, s, n) for (int i = int(n) - 1; i >= int(s); i--)
#define dforn(i, n) dforsn(i, 0, n)

using vi = vector<int>;
using ll = long long;
using ii = pair<int, int>;

#define fst first
#define snd second

#define sz(x) int(x.size())
#define all(x) begin(x), end(x)

#define pb push_back
#define eb emplace_back

const int N = 10000;
const int K = 15;

int up[K][N], depth[N];

int lca(int u, int v) {
    if (depth[u] < depth[v]) swap(u, v);
    int diff = depth[u] - depth[v];
    forn(i, K) if (diff >> i & 1) u = up[i][u];
    if (u == v) return u;
    dforn(i, K) if (up[i][u] != up[i][v]) {
        u = up[i][u], v = up[i][v];
    }
    return up[0][u];
}

int dist(int u, int v) {
    return depth[u] + depth[v] - 2 * depth[lca(u, v)];
}

int knownU, knownV;
int u, v;
int message;
vi pending;

int getOption() {
    int idx = 0;
    forn(i, sz(pending)) forsn(j, i + 1, sz(pending)) {
        if (minmax(pending[i], pending[j]) == minmax(u, v)) {
            u = knownU = pending[i], v = knownV = pending[j];
            return idx;
        }
        idx++;
    }
    forn(i, sz(pending)) {
        if (minmax(pending[i], knownV) == minmax(u, v)) {
            u = knownU = pending[i], v = knownV;
            return idx;
        }
        idx++;
    }
    forn(i, sz(pending)) {
        if (minmax(pending[i], knownU) == minmax(u, v)) {
            u = knownU, v = knownV = pending[i];
            return idx;
        }
        idx++;
    }
    return idx;
}

int send_message(int /*N*/, int i, int Pi) {
    if (i == 1) {
        depth[0] = 0;
        forn(j, K) up[j][0] = 0; 
        u = 0, v = 0;
        message = 0;
        knownU = 0, knownV = 0;
    }
    pending.pb(i);
    up[0][i] = Pi, depth[i] = depth[Pi] + 1;
    forn(j, K - 1) up[j + 1][i] = up[j][up[j][i]];
    if (dist(i, v) > dist(u, v)) u = i;
    else if (dist(i, u) > dist(u, v)) v = i;
    if (i < N - 17) return 0;
    if (i == N - 1) {
        vector<ii> candidates = {
            {knownU, N - 1},
            {knownU, N - 2},
            {N - 1, knownV},
            {N - 1, N - 2},
            {knownU, knownV}
        };
        int idx = 0;
        while (minmax(candidates[idx].fst, candidates[idx].snd) != minmax(u, v)) idx++;
        knownU = u, knownV = v;
        return idx;
    }
    if (i == N - 2) {
        vi candidates = {knownU, knownV, N - 2, N - 3, N - 4};
        int idx = 0;
        while (candidates[idx] != u) idx++;
        knownU = candidates[idx];
        return idx;
    }
    if (i == N - 5 || i == N - 17) {
        message = getOption();
        pending.clear();
    }
    int digit = message % 5;
    message /= 5;
    return digit;
}

ii getDiameter(int option, int U, int V) {
    forn(i, sz(pending)) forsn(j, i + 1, sz(pending)) {
        if (option-- == 0) return {pending[i], pending[j]};
    }
    forn(i, sz(pending)) {
        if (option-- == 0) return {pending[i], V};
    }
    forn(i, sz(pending)) {
        if (option-- == 0) return {U, pending[i]};
    }
    return {U, V};
}

ii longest_path(vi S) {
    int option = 0;
    dforsn(i, N - 17, N - 5) option = 5 * option + S[i];
    pending.clear();
    forsn(i, 1, N - 17 + 1) pending.pb(i);
    int U = 0, V = 0;
    tie(U, V) = getDiameter(option, U, V);
    option = 0;
    pending.clear();
    forsn(i, N - 17 + 1, N - 5 + 1) pending.pb(i);
    dforsn(i, N - 5, N - 2) option = 5 * option + S[i];
    tie(U, V) = getDiameter(option, U, V);
    U = vi{U, V, N - 2, N - 3, N - 4}[S[N - 2]];
    return vector<ii>{
            {U, N - 1},
            {U, N - 2},
            {N - 1, V},
            {N - 1, N - 2},
            {U, V}
    }[S[N - 1]];
}
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...