Pagini recente » Cod sursa (job #898040) | Cod sursa (job #417108) | Cod sursa (job #1240552) | Cod sursa (job #2676798) | Cod sursa (job #3321891)
#include <bits/stdc++.h>
using namespace std;
ifstream f("lca.in");
ofstream g("lca.out");
int tata[200009];
vector <int> v[200009];
int nivel[200009], first[200009];
struct elem
{
int nod, niv;
}rmq[1000009][22];
void dfs (int x, int t)
{
for (auto y:v[x])
{
if (y!=t)
{
nivel[y]=nivel[x]+1;
dfs (y, x);
}
}
}
int cnt=0;
void dfs2 (int nod, int t)
{
rmq[++cnt][0]={nod, nivel[nod]};
if (!first[nod]) first[nod]=cnt;
for (auto y:v[nod])
{
if (y!=t)
{
dfs2 (y, nod);
rmq[++cnt][0]={nod, nivel[nod]};
}
}
}
elem mini (elem x, elem y)
{
if (x.niv<=y.niv) return x;
else return y;
}
int ans (int x, int y)
{
x=first[x], y=first[y];
if (x>y) swap (x, y);
int l=y-x+1;
int poz=0, nr=1;
while (2*nr<=l)
{
poz++;
nr*=2;
}
elem z=mini (rmq[x][poz], rmq[y-(1<<poz)+1][poz]);
return z.nod;
}
signed main ()
{
int n, q;
f >> n >> q;
for (int i=2; i<=n; i++)
{
f >> tata[i];
v[tata[i]].push_back(i);
}
nivel[1]=1;
dfs (1, 0);
dfs2 (1, 0);
for (int i=1; (1<<i)<=cnt; i++)
{
for (int j=1; j+(1<<i)-1<=cnt; j++)
rmq[j][i]=mini(rmq[j][i-1], rmq[j+(1<<(i-1))][i-1]);
}
//for (int i=1; i<=cnt; i++) cout << rmq[i][0].nod << ' ';
//cout <<cnt;
while (q--)
{
int x, y;
f >> x >> y;
g << ans(x,y) << '\n';
}
}