Pagini recente » Cod sursa (job #2167912) | Cod sursa (job #2377182) | Cod sursa (job #1832539) | Cod sursa (job #599084) | Cod sursa (job #2403916)
#include <cstdio>
#include <vector>
#define nmax 100005
#define pb push_back
using namespace std;
FILE *fin=fopen("lca.in","r");
FILE *fout=fopen("lca.out","w");
vector<int>G[nmax];
int n, m, x;
int act, euler[2*nmax], h[2*nmax], first[nmax], ha;
int rmq[2*nmax][30], n1, n2, l, r;
void dfs(int k)
{
if (!first[k]) first[k] = act+1;
if (!G[k].size())
{
++act;
euler[act] = k;
h[act] = ha+1;
return;
}
for (int i=0; i<G[k].size(); ++i)
{
++act;
++ha;
euler[act] = k;
h[act] = ha;
dfs(G[k][i]);
++act;
euler[act] = k;
h[act] = ha;
--ha;
}
}
int l2(int x)
{
if (x<=1) return 0;
int ans = 0, act = 1;
while(true)
{
if (act > x)
return ans - 1;
++ans, act*=2;
}
}
int main()
{
fscanf(fin,"%d %d",&n,&m);
for (int i=2; i<=n; ++i)
{
fscanf(fin,"%d",&x);
G[x].pb(i);
}
dfs(1);
for (int i=1; i<=act; ++i)
rmq[i][0] = i;
for (int j=1; (1<<j)<=act; ++j)
for (int i=1; i+(1<<j)-1<=act; ++i)
if (h[rmq[i][j-1]] < h[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];
for (int i=1; i<=m; ++i)
{
fscanf(fin,"%d %d",&n1, &n2);
l = first[n1];
r = first[n2];
if (r < l) swap(l, r);
int dist = r - l + 1;
int wh = l2(dist);
int add = dist - (1<<wh);
if (h[rmq[l][wh]] < h[rmq[l+add][wh]])
fprintf(fout,"%d\n", euler[rmq[l][wh]]);
else
fprintf(fout,"%d\n", euler[rmq[l+add][wh]]);
}
fclose(fin);
fclose(fout);
return 0;
}