Pagini recente » Cod sursa (job #1804461) | Cod sursa (job #1498149) | Cod sursa (job #2543780) | Cod sursa (job #877857) | Cod sursa (job #2577698)
#include <bits/stdc++.h>
using namespace std;
ifstream fin("lca.in");
ofstream fout("lca.out");
int ap[100005], dads[100005], nivel[100005], pw[200005];
struct elem
{
int niv, poz;
}v[200005], rmq[200005][20];
vector <int> g[100005];
int n, m, k;
void dfs(int node)
{
nivel[node] = nivel[dads[node]] + 1;
v[++k].niv = nivel[node];
v[k].poz = node;
for(int i = 0; i < g[node].size(); i++)
{
dfs(g[node][i]);
v[++k].niv = nivel[node];
v[k].poz = node;
}
}
void rmqlca()
{
for(int i = 1; i <= k; i++)
rmq[i][0] = v[i];
pw[1] = 0;
for(int i = 2; i <= k; i++)
pw[i] = pw[i/2] + 1;
int q = 1;
for(int p = 1; p * 2 <= k; p *= 2)
{
for(int i = 1; i <= k - p*2 + 1; i++)
if(rmq[i][q - 1].niv < rmq[i + p][q - 1].niv)
rmq[i][q] = rmq[i][q-1];
else
rmq[i][q] = rmq[i + p][q - 1];
q++;
}
}
int lca(int a, int b)
{
a = ap[a];
b = ap[b];
if(a > b)
swap(a, b);
int l = b - a + 1;
if(rmq[a][pw[l]].niv < rmq[b - (1<<pw[l]) + 1][pw[l]].niv)
return rmq[a][pw[l]].poz;
else
return rmq[b - (1<<pw[l]) + 1][pw[l]].poz;
}
int main()
{
fin >> n >> m;
for(int i = 2; i <= n; i++)
{
fin >> dads[i];
g[dads[i]].push_back(i);
}
dfs(1);
rmqlca();
for(int i = 1; i <= k; i++)
if(ap[v[i].poz] == 0)
ap[v[i].poz] = i;
for(int i = 1; i <= m; i++)
{
int x, y;
fin >> x >> y;
fout << lca(x,y) << '\n';
}
return 0;
}