Cod sursa(job #2712282)

Utilizator xXoctavianXxStanescu Matei Octavian xXoctavianXx Data 25 februarie 2021 16:06:36
Problema Lowest Common Ancestor Scor 100
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 1.35 kb
#include <bits/stdc++.h>

using namespace std;

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

int n,m;
int t[100003];
int lev[100003];
vector<int> f[100003];
int euler[400003];
int nr;
int rmq[400003][20];
int poz[100003];

void dfs(int nod, int level)
{
    lev[nod] = level;
    euler[nr++]=nod;
    poz[nod]=nr-1;
    for(int i=0; i<f[nod].size(); i++)
    {
        dfs(f[nod][i],level+1);
        euler[nr++]=nod;
    }
}

inline void build_rmq()
{
    for(int i=0; i<nr; i++)
    {
        rmq[i][0]=euler[i];
    }
    int logdoinr = log2(nr);
    for(int j=1; j<=logdoinr; j++)
    {
        for(int i=0; i<nr-(1<<j); i++)
        {
            rmq[i][j]=rmq[i][j-1];
            if(lev[rmq[i][j-1]]>lev[rmq[i+(1<<(j-1))][j-1]])
                rmq[i][j]=rmq[i+(1<<(j-1))][j-1];
        }
    }
}

int query(int a, int b)
{
    a=poz[a];
    b=poz[b];
    if(a>b) swap(a,b);
    int lg=log2(b-a+1);
    int rasp = rmq[a][lg];
    if(lev[rmq[a][lg]] > lev[rmq[b-(1<<lg)+1][lg]]) rasp = rmq[b-(1<<lg)+1][lg];
    return rasp;
}

int main()
{
    fin>>n>>m;
    for(int i=2; i<=n; i++)
    {
        fin>>t[i];
        f[t[i]].push_back(i);
    }
    dfs(1,0);
    build_rmq();
    for(int i=0; i<m; i++)
    {
        int x,y;
        fin>>x>>y;
        fout<<query(x,y)<<"\n";
    }
    return 0;
}