Cod sursa(job #739739)

Utilizator ColcerPaulColcer Paul ColcerPaul Data 23 aprilie 2012 20:10:03
Problema Lowest Common Ancestor Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 1.21 kb
#include<fstream>
#include<vector>
using namespace std;

ifstream f("lca.in");
ofstream g("lca.out");

#define MAX 200100

int n, m, RMQ[20][MAX];
int euler[MAX], nivel[MAX];

vector<int> vec[MAX];


void dfs(int nod){
    int i;
    euler[++euler[0]] = nod;
    nivel[nod] = euler[0];
    for(i = 0; i < (int)vec[nod].size(); ++i){
        dfs(vec[nod][i]);
        euler[++euler[0]] = nod;
    }

}

void rmq(){
    for(int i = 1; i < euler[0]; ++i)
        RMQ[0][i] = euler[i];

    for(int i = 1; (1 << i) <= euler[0]; ++i)
        for(int j = 1; j <= euler[0] - (1<<i) + 1; ++j)
            RMQ[i][j] = min(RMQ[i-1][j], RMQ[i-1][j + (1 << (i-1))]);


}

int query(int a, int b){
    int x, y, i;
    x = nivel[a];
    y = nivel[b];

    if(x > y)
        swap(x, y);
    for( i = 1; (1 << i) <= (y-x+1); ++i);
        --i;
    return min(RMQ[i][x], RMQ[i][y - (1 << i) + 1]);
}

int main(){
    int x, y;
    f>>n>>m;

    for(int i = 2; i <= n; ++i){
        f>>x;
        vec[x].push_back(i);
    }

    dfs(1);
    rmq();

    for(int i = 1; i <= m; ++i){
        f>>x>>y;
        g<<query(x, y)<<"\n";
    }

    f.close();
    g.close();
    return 0;
}