Pagini recente » Borderou de evaluare (job #2220503) | Cod sursa (job #466704) | Cod sursa (job #2774896) | Cod sursa (job #1024018) | Cod sursa (job #3274359)
#include <bits/stdc++.h>
using namespace std;
ifstream fin("lca.in");
ofstream fout("lca.out");
int n, q, i, p[100002][20], x, y;
int tIn[100002], tOut[100002];
vector<int> g[100002];
int timp = 0;
static inline void Parc(int nod = 1, int tata = 0) {
tIn[nod] = ++timp;
for(int urm : g[nod]) {
if(urm != tata) Parc(urm, nod);
}
tOut[nod] = ++timp;
}
static inline void Precalc() {
for(int put = 1; put < 20; put++) {
for(int i = 1; i <= n; i++) p[i][put] = p[p[i][put - 1]][put - 1];
}
}
static inline bool Subarb(int tata, int nod) {
return tIn[tata] <= tIn[nod] && tOut[tata] >= tOut[nod];
}
static inline int Calc(int x, int y) {
if(Subarb(x, y)) return x;
if(Subarb(y, x)) return y;
for(int put = 19; put >= 0; put--) {
int z = p[x][put];
if(z != 0 && !Subarb(z, y)) x = z;
}
return p[x][0];
}
int main() {
ios_base::sync_with_stdio(false);
fin.tie(nullptr);
fout.tie(nullptr);
fin >> n >> q;
for(i = 2; i <= n; i++) {
int t;
fin >> t;
p[i][0] = t;
g[t].push_back(i);
}
Parc();
Precalc();
while(q--) {
fin >> x >> y;
fout << Calc(x, y) << "\n";
}
return 0;
}