Cod sursa(job #2072865)

Utilizator papinub2Papa Valentin papinub2 Data 22 noiembrie 2017 12:48:44
Problema Lowest Common Ancestor Scor 20
Compilator cpp Status done
Runda Arhiva educationala Marime 1.31 kb
#include <fstream>
#include <vector>

using namespace std;

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

const int Nmax = 100005;

int n, m, x, y, log1, log2;
int nivel[Nmax];
int dp[20][Nmax];

vector <int> A[Nmax];

void DFS (int nod, int niv)
{
    nivel[nod] = niv;

    for (int i = 0; i < A[nod].size(); i++)
        DFS(A[nod][i], niv + 1);
}

int lca (int x, int y)
{
    if (nivel[x] < nivel[y])
        swap (x, y);

    for (log1 = 1; (1<<log1) < nivel[x]; log1++);
    for (log2 = 1; (1<<log1) < nivel[y]; log2++);

    for (int i = log1; i >= 0; i--)
        if (nivel[x] - (1<<i) >= nivel[y])
            x = dp[i][x];

    if (x == y)
        return x;

    for (int i = log2; i >= 0; i--)
        if (dp[i][x] && dp[i][x] != dp[i][y])
        {
            x = dp[i][x];
            y = dp[i][y];
        }

    return dp[0][y];
}

int main()
{
    in >> n >> m;

    for (int i = 1; i <= n - 1; i++)
    {
        in >> x;

        A[x].push_back(i + 1);
        dp[0][i + 1] = x;
    }

    DFS(1, 0);

    for (int i = 1; (1<<i) <= n; i++)
        for (int j = 1; j <= n; j++)
            dp[i][j] = dp[i-1][dp[i-1][j]];

    for (int i = 1; i <= m; i++)
    {
        in >> x >> y;
        out << lca (x, y) << '\n';
    }

    return 0;
}