Submission #1368188

#TimeUsernameProblemLanguageResultExecution timeMemory
1368188llmMigrations (IOI25_migrations)C++20
20 / 100
29 ms1028 KiB
#include <iostream>
#include <vector>
#include <algorithm>

using namespace std;

// Sender's global state
static int depth_arr[10005];
static int up[10005][15];
static int U_curr = 0, V_curr = 0;
static int max_dist = 0;
static int U_prev = 0;

int get_lca(int u, int v) {
    if (depth_arr[u] < depth_arr[v]) swap(u, v);
    for (int j = 14; j >= 0; --j) {
        if (depth_arr[u] - (1 << j) >= depth_arr[v]) {
            u = up[u][j];
        }
    }
    if (u == v) return u;
    for (int j = 14; j >= 0; --j) {
        if (up[u][j] != up[v][j]) {
            u = up[u][j];
            v = up[v][j];
        }
    }
    return up[u][0];
}

int get_dist(int u, int v) {
    return depth_arr[u] + depth_arr[v] - 2 * depth_arr[get_lca(u, v)];
}

int send_message(int N, int i, int Pi) {
    if (i == 1) {
        U_curr = 0; 
        V_curr = 0; 
        max_dist = 0;
        depth_arr[0] = 0;
        for (int j = 0; j <= 14; ++j) up[0][j] = 0;
    }

    depth_arr[i] = depth_arr[Pi] + 1;
    up[i][0] = Pi;
    for (int j = 1; j <= 14; ++j) {
        up[i][j] = up[up[i][j - 1]][j - 1];
    }

    int dU = get_dist(i, U_curr);
    int dV = get_dist(i, V_curr);

    // Strictly track the true online diameter
    if (dU > max_dist || dV > max_dist) {
        if (dU >= dV) {
            V_curr = i; 
            max_dist = dU;
        } else {
            U_curr = i; 
            max_dist = dV;
        }
    }

    // Delay all communication until the final two steps
    if (i == N - 2) {
        U_prev = U_curr;
        return U_curr + 1;
    } else if (i == N - 1) {
        if (U_curr == U_prev) {
            // U survived, so the other endpoint is V_curr
            return V_curr + 1;
        } else {
            // U was replaced by N-1. To signal this, we add 10000 to V_curr
            return V_curr + 10001;
        }
    }
    
    return 0;
}

std::pair<int, int> longest_path(std::vector<int> S) {
    int N = S.size();
    
    // The Museum only needs to look at the very last two messages
    int val1 = S[N - 2];
    int val2 = S[N - 1];
    
    int U = val1 - 1;
    int V = 0;
    
    if (val2 > 10000) {
        V = val2 - 10001;
        U = N - 1; // U was replaced by the final node
    } else {
        V = val2 - 1;
    }
    
    return {U, V};
}
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...