Pagini recente » Cod sursa (job #1182502) | Cod sursa (job #1185347) | Cod sursa (job #2788643) | Cod sursa (job #2060891) | Cod sursa (job #885795)
Cod sursa(job #885795)
#include <fstream>
#include <iostream>
#include <vector>
#define nmax 100001
using namespace std;
ifstream f("lca.in");
ofstream g("lca.out");
vector <int> vec[nmax];
int n,k=1,level[2*nmax],e[2*nmax],first[nmax],lg[2*nmax];
int rmq[20][2*nmax];
void euler(int nod,int lev)
{
e[k]=nod;
level[k]=lev;
if(!first[nod]) first[nod]=k;
k++;
int i;
for(i=0;i<vec[nod].size();i++)
{
euler(vec[nod][i],lev+1);
e[k]=nod;
level[k]=lev;
k++;
}
}
void rangemin()
{
int i,j;
for(i=1;i<=k;i++) rmq[0][i]=i;
for(i=1;(1<<i)<=k;i++)
{
for(j=1;j<=k;j++)
{
if(j+(1<<(i-1))<=k && level[rmq[i-1][j]]>level[rmq[i-1][j+(1<<(i-1))]])
rmq[i][j]=rmq[i-1][j+(1<<(i-1))];
else rmq[i][j]=rmq[i-1][j];
}
}
}
int lca(int x, int y)
{
int a,b,dif,sol;
a=first[x]; b=first[y];
if(a>b) swap(a,b);
dif=b-a+1;
sol=rmq[lg[dif]][a];
if(dif-(1<<lg[dif]) && level[rmq[lg[dif]][a+dif-(1<<lg[dif])]]<level[sol])
sol=rmq[lg[dif]][a+dif-(1<<lg[dif])];
return e[sol];
}
int main()
{
int i,j,m,x,y;
f>>n>>m;
for(i=2;i<=n;i++)
{
f>>x;
vec[x].push_back(i);
}
euler(1,1); k-=1;
rangemin();
lg[1]=0;
for(i=2;i<=k;i++) lg[i]=lg[i/2]+1;
for(i=0;i<m;i++)
{
f>>x>>y;
g<<lca(x,y)<<'\n';
}
}