Cod sursa(job #2928204)

Utilizator AlexNicuNicu Alexandru AlexNicu Data 22 octombrie 2022 14:03:40
Problema Lowest Common Ancestor Scor 0
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 1.45 kb
include <fstream>
#include <vector>
#include <cmath>
 
using namespace std;
 
#define NMAX (int)1e5
#define MAXLOG 17
 
int start[NMAX + 5], endd[NMAX + 5];
 
int up[NMAX + 5][MAXLOG + 1];
 
int timer, logg2;
 
vector<int> G[NMAX + 5];
 
void DFS(int node, int father) {
    start[node] = ++timer;
    up[node][0] = father;
    for (int i = 1; i <= logg2; i++) {
        up[node][i] = up[up[node][i - 1]][i - 1];
    }
    for (auto child : G[node]) {
        if (child != father) {
            DFS(child, node);
        }
    }
    endd[node] = ++timer;
}
 
bool is_stramos(int node1, int node2) {
    return start[node1] <= start[node2] && endd[node1] >= endd[node2];
}
 
int LCA(int node1, int node2) {
    if (is_stramos(node1, node2))
        return node1;
    if (is_stramos(node2, node1))
        return node2;
    for (int i = logg2; i >= 0; i--) {
        if (!is_stramos(up[node1][i], node2)) {
            node1 = up[node1][i];
        }
    }
    return up[node1][0];
}
 
void preprocess(int n) {
    timer = 0;
    logg2 = log2(n);
    DFS(1, 1);
}
 
ifstream cin("lca.in");
ofstream cout("lca.out");
 
int main()
{
    int n, m, node, node1, node2;
    cin >> n >> m;
    for (int i = 1; i <= n - 1; i++) {
        cin >> node;
        G[node].push_back(i + 1);
    }
    preprocess(n);
    for (int i = 1; i <= m; i++) {
        cin >> node1 >> node2;
        cout << LCA(node1, node2) << "\n";
    }
}