Cod sursa(job #3348124)

Utilizator sasha-vovcSasha Vovcenco sasha-vovc Data 19 martie 2026 19:51:03
Problema Lowest Common Ancestor Scor 100
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 1.5 kb
#include <iostream>
#include <fstream>
#include <vector>
#include <cmath>
using namespace std;

ifstream in("lca.in");
ofstream out("lca.out");

vector<vector<int>> adj;
int nodes[200002];
int depth[200002];
int timer = 0;
int last[100001];

void visit(int i, int d) {
    nodes[timer] = i;
    depth[timer] = d;
    last[i] = timer;
    timer++;
}

void dfs(int i, int d = 0) {
    visit(i, d);

    for (int j : adj[i]) {
        dfs(j, d + 1);
        visit(i, d);
    }
}

int dp[18][200002];

void sparse(int m) {
    for (int j = 1; j <= m; j++) {
        dp[0][j] = j;
    }

    int n = floor(log2(m)) + 1;
    for (int i = 1; i < n; i++) {
        for (int j = 0; j < m; j++) {
            int k = 1 << (i - 1);
            if (j + k >= m) continue;

            if (depth[dp[i - 1][j]] < depth[dp[i - 1][j + k]]) {
                dp[i][j] = dp[i - 1][j];
            } else {
                dp[i][j] = dp[i - 1][j + k];
            }
        }
    }
}


int main() {
    int n, m;
    in >> n >> m;
    adj = vector<vector<int>>(n + 1);

    for (int k = 2; k <= n; k++) {
        int j;
        in >> j;
        adj[j].push_back(k);
    }

    dfs(1);

    sparse(2 * n - 1);
    while (m--) {
        int l1, r1;
        in >> l1 >> r1;

        int l = last[l1];
        int r = last[r1];
        if (l > r) swap(l, r);

        int p = floor(log2(r - l + 1));
        int k = 1 << p;

        int lca = depth[dp[p][l]] < depth[dp[p][r - k + 1]] ? dp[p][l] : dp[p][r - k + 1];
        out << nodes[lca] << '\n';
    }
}