Cod sursa(job #2951339)

Utilizator AndreibatmanAndrei Croitoriu Andreibatman Data 6 decembrie 2022 01:02:35
Problema Lowest Common Ancestor Scor 100
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 1.19 kb
#include <bits/stdc++.h>
using namespace std;
ifstream fin("lca.in");
ofstream fout("lca.out");
vector<int>v[100010];
int rmq[200010][20],level[200010],euler[200010],first[100010],lg,k,n,i,j,x,q,a,b;
void dfs(int nod,int nivel)
{
    euler[++lg]=nod;
    rmq[lg][0]=lg;
    level[lg]=nivel;
    if(first[nod]==0)
        first[nod]=lg;
    for(auto it:v[nod])
    {
        dfs(it,nivel+1);
        euler[++lg]=nod;
        rmq[lg][0]=lg;
        level[lg]=nivel;
    }
}
int lca(int x,int y)
{
    x=first[x];
    y=first[y];
    if(x>y)
        swap(x,y);
    k=floor(log2(y-x+1));
    int ans;
    if(level[rmq[x][k]]<level[rmq[y-(1<<k)+1][k]])
        ans=rmq[x][k];
    else ans=rmq[y-(1<<k)+1][k];
    return euler[ans];
}
int main()
{
    fin>>n>>q;
    for(i=2;i<=n;i++)
    {
        fin>>x;
        v[x].push_back(i);
    }
    dfs(1,0);
    for(j=1;(1<<j)<=lg;j++)
        for(i=1;i+(1<<j)-1<=lg;i++)
            if(level[rmq[i][j-1]]<level[rmq[i+(1<<(j-1))][j-1]])
                rmq[i][j]=rmq[i][j-1];
            else rmq[i][j]=rmq[i+(1<<(j-1))][j-1];
    while(q--)
    {
        fin>>a>>b;
        fout<<lca(a,b)<<'\n';
    }
    return 0;
}