Pagini recente » Cod sursa (job #2835940) | Statistici Ioana Pozinarea (IoanaPozinarea) | Match | Cod sursa (job #750933) | Cod sursa (job #379849)
Cod sursa(job #379849)
#include <algorithm>
#include <vector>
using namespace std;
#define DIM 100001
#define LOG 21
#define pb push_back
#define sz size()
int n, m, cnt, lg[ 2*DIM ], eul[ 2*DIM ], rng[ 2*DIM ], first[ DIM ], rmq[ LOG ][ 4*DIM ];
vector <int> vec[ DIM ];
void dfs( int nod, int lvl ) {
unsigned int I;
eul[ ++cnt ] = nod;
rng[ cnt ] = lvl;
first[ nod ] = cnt;
for( I = 0; I < vec[ nod ].sz; ++I ) {
dfs( vec[ nod ][ I ], lvl+1 );
eul[ ++cnt ] = nod;
rng[ cnt ] = lvl;
}
}
void build_rmq() {
int i, j;
for( i = 2; i <= cnt; ++i )
lg[ i ] = lg[ i>>1 ] + 1;
for( i = 1; i <= cnt; ++i )
rmq[ 0 ][ i ] = i;
for( i = 1; ( 1<<i ) < cnt; ++i )
for( j = 1; j <= cnt - ( 1<<i ); ++j ) {
rmq[ i ][ j ] = rmq[ i-1 ][ j ];
if( rng[ rmq[ i-1 ][ j + ( 1<<( i-1 ) ) ] ] < rng[ rmq[ i ][ j ] ] )
rmq[ i ][ j ] = rmq[ i-1 ][ j + ( 1<<( i-1 ) ) ];
}
}
int lca( int x, int y ) {
int a, b, l, dif, rez;
a = first[ x ];
b = first[ y ];
if( a > b )
swap( a, b );
dif = b-a+1;
l = lg[ dif ];
rez = rmq[ l ][ a ];
if( rng[ rmq[ l ][ b-( 1<<l )+1 ] ] < rng[ rez ] )
rez = rmq[ l ][ b-( 1<<l )+1 ];
return eul[ rez ];
}
int main() {
freopen( "lca.in", "r", stdin );
freopen( "lca.out", "w", stdout );
int i, x, y;
scanf( "%d %d", &n, &m );
for( i = 2; i <= n; ++i ) {
scanf( "%d", &x );
vec[ x ].pb( i );
}
dfs( 1, 0 );
build_rmq();
for( i = 1; i <= m; ++i ) {
scanf( "%d %d", &x, &y );
printf( "%d\n", lca( x, y ) );
}
return 0;
}