Pagini recente » Cod sursa (job #1346714) | Cod sursa (job #1621839) | Cod sursa (job #602854) | Cod sursa (job #2297553) | Cod sursa (job #2367788)
#include <bits/stdc++.h>
using namespace std;
ifstream fi("lca.in");
ofstream fo("lca.out");
const int NMAX = 1e5 + 5;
const int LOG = 25;
struct multe
{
int val, poz;
};
vector <int> G[NMAX];
int p[NMAX], niv[NMAX];
int n, m;
vector <int> repr;
multe rmq[LOG][2 * NMAX];
int pr[NMAX];
int lg[NMAX];
void calcLg()
{
lg[1] = 0;
for (int i = 2; i <= n; i++)
if ((1 << (lg[i - 1] + 1)) <= i)
lg[i] = lg[i - 1] + 1;
else
lg[i] = lg[i - 1];
}
void dfs(int nod)
{
repr.push_back(nod);
pr[nod] = repr.size() - 1;
for (auto v: G[nod])
{
niv[v] = niv[nod] + 1;
dfs(v);
repr.push_back(nod);
}
}
void getRmq()
{
int l = repr.size();
for (int j = 0; j < l; j++)
rmq[0][j] = {niv[repr[j]], repr[j]};
for (int i = 1; (1 << i) <= l; i++)
{
for (int j = 0; j < l; j++)
if (j + (1 << i) - 1 < l) /// intra
{
if (rmq[i - 1][j].val < rmq[i - 1][j + (1 << (i - 1))].val)
rmq[i][j] = rmq[i - 1][j];
else
rmq[i][j] = rmq[i - 1][j + (1 << (i - 1))];
}
}
}
int getMin(int a, int b)
{
int d = lg[b - a + 1];
if (rmq[d][a].val < rmq[d][b - (1 << d) + 1].val)
return rmq[d][a].poz;
return rmq[d][b - (1 << d) + 1].poz;
}
int main()
{
fi >> n >> m;
for (int i = 2; i <= n; i++)
{
fi >> p[i];
G[p[i]].push_back(i);
}
dfs(1);
calcLg();
getRmq();
while (m--)
{
int u, v;
fi >> u >> v;
if (pr[u] > pr[v])
swap(u, v);
if (u == v)
fo << u << "\n";
else
fo << getMin(pr[u], pr[v]) << "\n";
}
return 0;
}