Pagini recente » Cod sursa (job #1248203) | Cod sursa (job #2495712) | Cod sursa (job #2667264) | Cod sursa (job #709357) | Cod sursa (job #2929839)
#include <fstream>
#include <vector>
using namespace std;
ifstream fin("lca.in");
ofstream fout("lca.out");
inline int Log2(int n){
int Log2 = 0;
while(n > 1){
Log2 ++;
n /= 2;
}
return Log2;
}
int n, m;
const int NMAX = 100002;
vector<int> V[NMAX];
int euler[2*NMAX], cnt, Level[NMAX], First[NMAX];
bool viz[NMAX];
void DFSEuler(int node, int level){
euler[++cnt] = node;
Level[cnt] = level;
First[node] = cnt;
viz[node] = true;
for(int i = 0; i < V[node].size(); i++){
if(!viz[V[node][i]]){
DFSEuler(V[node][i], level+1);
euler[++cnt] = node;
Level[cnt] = level;
}
}
}
int RMQ[17][NMAX*2];
void buildRMQ(){
for(int i = 1; i <= cnt; i++){
RMQ[0][i] = i;
}
for(int i = 1; i <= Log2(cnt); i++){
for(int j = 1; j <= cnt-(1<<i); j++){
if(Level[RMQ[i-1][j]] < Level[RMQ[i-1][j + (1 << (i-1))]]){
RMQ[i][j] = RMQ[i-1][j];
}
else
RMQ[i][j] = RMQ[i-1][j + (1 << (i-1))];
}
}
}
int LCA(int u, int v){
if(First[u] > First[v]){
swap(u, v);
}
u = First[u];
v = First[v];
int DiffLog = Log2(v - u + 1);
if(Level[RMQ[DiffLog][u]] < Level[RMQ[DiffLog][v - (1 << DiffLog) + 1]]){
return euler[RMQ[DiffLog][u]];
}
return euler[RMQ[DiffLog][v - (1 << DiffLog) + 1]];
}
int main(){
fin >> n >> m;
for (int i = 2; i <= n; i++)
{
int ancestor_of_i;
fin >> ancestor_of_i;
V[ancestor_of_i].push_back(i);
}
DFSEuler(1, 0);
buildRMQ();
/*for(int i=1; i<=cnt; i++){
fout << Level[i] << " ";
}
fout << "\n";
for(int i=0; i<=Log2(cnt); i++){
for(int j=1; j<=cnt - (1<<i); j++){
fout << RMQ[i][j] << " ";
}
fout << "\n";
}*/
for(int q = 1; q <= m; q++){
int node1, node2;
fin >> node1 >> node2;
fout << LCA(node1, node2) << '\n';
}
return 0;
}