Pagini recente » Cod sursa (job #649310) | Cod sursa (job #496822) | Cod sursa (job #2115301) | Cod sursa (job #2883021) | Cod sursa (job #3231281)
#include<fstream>
#include<vector>
std::ifstream fin("lca.in");
std::ofstream fout("lca.out");
const int NMAX=100001;
int e[2*NMAX-1], l[2*NMAX-1], h[NMAX];
int rmq[2*NMAX-1][20];
int lg[2*NMAX-1];
std::vector<int>g[NMAX];
int n, q;
void read()
{
fin>>n>>q;
for(int i=1; i<n; ++i)
{
int node;
fin>>node;
g[node].push_back(i+1);
}
}
int k=1;
void euler(int node, int depth)
{
e[k]=node;
if(!h[node])
h[node]=k;
l[k++]=depth;
for(auto &it:g[node])
{
euler(it, depth+1);
e[k]=node;
l[k++]=depth;
}
}
void precalc()
{
lg[1]=0;
for(int i=2; i<2*NMAX-1; ++i)
lg[i]=lg[i/2]+1;
for(int i=1; i<=2*n-1; ++i)
rmq[i][0]=i;
for(int i=1; (1<<i)<=2*n-1; ++i)
for(int j=1; j<=(2*n-1)-(1<<i)+1; ++j)
{
int val=(1<<(i-1));
int a=l[rmq[j][i-1]];
int b=l[rmq[j+val][i-1]];
if(a<b)
rmq[j][i]=rmq[j][i-1];
else
rmq[j][i]=rmq[j+val][i-1];
}
}
void solve()
{
for(int i=0; i<q; ++i)
{
int u, v;
fin>>u>>v;
if(h[v]<h[u])
std::swap(u, v);
int dist=h[v]-h[u]+1;
int aux=lg[dist], rem=dist-(1<<aux);
fout<<std::min(e[rmq[h[u]][aux]], e[rmq[h[u]+rem][aux]])<<'\n';
}
}
int main()
{
read();
euler(1, 0);
precalc();
solve();
return 0;
}