Pagini recente » Cod sursa (job #1484462) | Cod sursa (job #1658153) | Cod sursa (job #331457) | Cod sursa (job #1350448) | Cod sursa (job #3308807)
#include <bits/stdc++.h>
#define int long long
using namespace std;
ifstream fin ("lca.in");
ofstream fout ("lca.out");
int tata[200005];
int lvl[200005];
vector <int> gr[200005];
vector <int> Euler;
vector <int> v;
int viz[200005];
pair <int,int> dp[22][200005];
int lg[200005];
void DFS(int I){
Euler.push_back(I);
viz[I] = 1;
for (auto son:gr[I]){
if (viz[son]) continue;
DFS(son);
Euler.push_back(I);
}
}
void PreCalc_Log(int n){
lg[1] = 0;
for (int i=2;i<=n;++i){
lg[i] = lg[i/2]+1;
}
}
signed main()
{
int n,m;
fin >> n >> m;
lvl[1] = 1;
tata[1] = 1;
for (int i=2;i<=n;++i){
fin >> tata[i];
lvl[i] = lvl[tata[i]]+1;
gr[tata[i]].push_back(i);
}
DFS(1);
int N = Euler.size();
v.push_back(0);
for (auto x:Euler){
v.push_back(lvl[x]);
}
v.push_back(1e9);
Euler.push_back(1e9);
for (int i=1;i<=N;++i){
dp[0][i] = min(make_pair(v[i],Euler[i]),make_pair(v[i+1],Euler[i+1]));
}
for (int i=1;i<20;++i){
for (int j=1;j<=N;++j){
if (j+(1<<i)>N) continue;
int a = dp[i-1][j].second;
int b = dp[i-1][j+(1<<(i-1))].second;
if (a<b){
dp[i][j] = dp[i-1][j];
}else{
dp[i][j] = dp[i-1][j+(1<<(i-1))];
}
}
}
PreCalc_Log(N);
vector <int> st(N+5,0);
for (int i=0;i<N;++i){
int x = Euler[i];
if (st[x]==0){
st[x] = i+1;
}
}
for (int i=1;i<=m;++i){
int L,R;
fin >> L >> R;
L = st[L];
R = st[R];
if (L>R) swap(L,R);
if (L==R){
fout << Euler[L] << '\n'; // caz particular
continue;
}
int p = lg[R-L];
//pair <int,int> ans = min(dp[p][L],dp[p][R-(1<<p)]);
pair <int,int> ans;
if (dp[p][L].second<dp[p][R-(1<<p)].second) ans = dp[p][L];
else ans = dp[p][R-(1<<p)];
fout << ans.second << '\n';
}
return 0;
}