Cod sursa(job #385379)

Utilizator ConsstantinTabacu Raul Consstantin Data 22 ianuarie 2010 17:52:15
Problema Lowest Common Ancestor Scor 0
Compilator cpp Status done
Runda Arhiva educationala Marime 1.06 kb
#include<stdio.h>
#include<vector>

using namespace std;

vector<int> v[100010];

int rmq[ 20 ][ 100010 <<1],n,i,j,k,m,tata[10010],a,b,l[100010],poz[100010];
void dfs(int nod){
int i = 0,n,x;
n = v[nod].size();
m++;
if(!l[nod])l[nod] = l[tata[nod]] + 1;
	if(!poz[nod])poz[nod] = m;
rmq[0][m] = nod;
for(i = 0 ;i  < n ;i++)
	{
	
	
	x = v[nod][i];
	dfs(x);
	m++;
	rmq[0][m] = nod;
	}
}
int min(int a,int b){
if(l[a] < l[b])
	return a;
return b;
}


int querry(int a,int b){
int k =0,m;
a = poz[a];
b = poz[b];

if(b<a){
	m=a;a=b;b=m;}

while(a+(1<<k) <= b)
	k++;
k--;
return min(rmq[k][a],rmq[k][b-(1<<k)]);
}


int main(){
freopen("lca.in","r",stdin);
freopen("lca.out","w",stdout);

scanf("%d %d",&n,&k);
for(i = 1; i < n ;i++)
	{scanf("%d",&tata[i+1]);
	v[tata[i+1]].push_back(i+1);
	}

dfs(1);
l[0] = 10000;
for(i = 1; (1 << i) <= m ; i++)
	for(j = 1 ;j + (1<<i) <= m; j++)
		rmq[i][j] = min(rmq[i-1][j],rmq[i-1][j+(1<<i)-1]);
for(i = 1 ; i <= k  ;i++)
	{scanf("%d %d",&a,&b);
	printf("%d\n",querry(a,b));}
return 0;}