Cod sursa(job #3306399)

Utilizator razvanmrt_06Mariuta Razvan razvanmrt_06 Data 10 august 2025 12:16:11
Problema Lowest Common Ancestor Scor 10
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 1.72 kb
#include <iostream>
#include <fstream>
#include <vector>

using namespace std;

const int Nmax = 100001;

int n, m, firstApp[Nmax], depth[Nmax], log2[Nmax], dp[Nmax][22], lenE;
//dp[i][j] = nodul cu depth minim pe [i, i + 2^j - 1] pe vectorul E

vector<int> L[Nmax], E;

void dfs(int nod){
    E.push_back(nod);
    firstApp[nod] = E.size() - 1;
    for(auto son : L[nod]){
        depth[son] = depth[nod] + 1;
        dfs(son);
        E.push_back(nod);
    }
}

void preCalc(){
    log2[1] = 0;
    for(int i = 2; i <= n; i++){
        log2[i] = log2[i/2] + 1;
    }
}

void RMQ(){
    for(int i = 0; i < lenE; i++){
        dp[i][0] = E[i];
    }

    for(int p = 1; (1 << p) < lenE; p++){
        for(int i = 0; i < lenE; i++){
            dp[i][p] = dp[i][p-1];
            int j = i + (1 << (p-1));
            if(j < lenE && (depth[dp[i][p]]> depth[dp[j][p-1]])){
                dp[i][p] = dp[j][p-1];
            }
        }
    }
}

int solve(int u, int v){
    int poz1 = firstApp[u];
    int poz2 = firstApp[v];
    if(poz1 > poz2){
        swap(poz1, poz2);
    }
    int dif = poz2 - poz1 + 1;
    int p = log2[dif];
    int min1 = dp[poz1][p];
    int min2 = dp[poz2 - (1 << p) + 1][p];
    if(depth[min1] < depth[min2]){
        return min1;
    }
    return min2;
}

int main()
{
    ifstream fin("lca.in");
    ofstream fout("lca.out");
    fin >> n >> m;
    for(int i = 2; i <= n; i++){
        int aux;
        fin >> aux;
        L[aux].push_back(i);
    }

    depth[1] = 0;
    dfs(1);
    preCalc();
    lenE = E.size();
    RMQ();

    while(m--){
        int u, v;
        fin >> u >> v;
        fout << solve(u, v) << "\n";
    }

    return 0;
}