Cod sursa(job #1807899)

Utilizator VictoriaNevTascau Victoria VictoriaNev Data 17 noiembrie 2016 00:57:34
Problema Lowest Common Ancestor Scor 10
Compilator cpp Status done
Runda Arhiva educationala Marime 1.44 kb
#include <fstream>
#include <vector>
using namespace std;
const int NMAX=100005;
vector<int> vertex[NMAX];
int euclid[NMAX*2], len[NMAX*2], pos[NMAX];
int rmq[20][NMAX*2], niv[NMAX*2];
int k, n;

void dfs(int nod, int nivel)
{
    euclid[++k] = nod;
    niv[k] = nivel;
    pos[nod] = k;
    for (int i = 0; i < vertex[nod].size(); ++i)
    {
        int x = vertex[nod][i];
        dfs(x, nivel + 1);
        euclid[++k] = nod;
        niv[k] = nivel;
    }
}


int main()
{
    ifstream in("lca.in");
    ofstream out("lca.out");
    int m, sol, p;
    in >> n >> m;
    for (int i = 2; i <= n; ++i)
    {
        int x;
        in >> x;
        vertex[x].push_back(i);
    }

    dfs(1, 0);

    len[1] = 0;
    for(int i = 2; i <= k; i++)
        len[i] = 1 + len[i / 2];

    for(int i = 1; i <= k; i++)
        rmq[0][i] = i;
    for(int i = 1; (1 << i) <= k; i++)
        for(int j = 1; j - (1 << i) + 1 <= k; j++)
        {
            p = 1 << (i - 1);
            rmq[i][j] = rmq[i - 1][j];
            if(niv[rmq[i - 1][j]] > niv[rmq[i - 1][j + p]])
                rmq[i][j] = rmq[i - 1][j + p];
        }

    while (m--)
    {
        int x, y;
        in >> x >> y;
        x = pos[x];
        y = pos[y];
        if(x > y)
            swap(x, y);
        p = len[y - x + 1];
        sol = rmq[p][x];
        if(niv[sol] > niv[rmq[p][y - 1 << p + 1]])
            sol = rmq[p][y - (1 << p) + 1];
        out << euclid[sol] << '\n';
    }

    return 0;
}