Pagini recente » Cod sursa (job #2860830) | Cod sursa (job #835580) | Cod sursa (job #3150913) | Cod sursa (job #891469) | Cod sursa (job #1912633)
#include <fstream>
#include <vector>
#include <algorithm>
#include <stack>
#define ll long long
#define N 100002
using namespace std;
ifstream fin("lca.in");
ofstream fout("lca.out");
struct Nod { int level, firstPos; vector<int> v; };
int v[N * 3];
int rmq[20][N * 3];
Nod node[N];
void Euler(int nod, int level)
{
node[nod].firstPos = ++v[0];
node[nod].level = level;
v[v[0]] = nod;
for (int i = 0; i < node[nod].v.size(); i++)
if (!node[node[nod].v[i]].firstPos)
{
Euler(node[nod].v[i], level + 1);
v[++v[0]] = nod;
}
}
void CreateRMQ()
{
for (int j = 1; j <= v[0]; j++)
rmq[0][j] = v[j];
for (int i = 1, pow = 2; pow <= v[0]; i++, pow <<= 1)
{
for (int j = 1; j <= v[0] - pow + 1; j++)
if (node[rmq[i - 1][j]].level < node[rmq[i - 1][j + pow / 2]].level)
rmq[i][j] = rmq[i - 1][j];
else
rmq[i][j] = rmq[i - 1][j + pow / 2];
}
}
int querry(int st, int dr)
{
if (st > dr)
swap(st, dr);
int pow = 0;
while (1 << pow <= dr - st + 1)
pow++;
pow--;
if (node[rmq[pow][st]].level < node[rmq[pow][dr - (1 << pow) + 1]].level)
return rmq[pow][st];
else
return rmq[pow][dr - (1 << pow) + 1];
}
int main()
{
int n, m, n1, n2, nod;
fin >> n >> m;
for (int i = 2; i <= n; i++)
{
fin >> nod;
node[nod].v.push_back(i);
}
Euler(1, 1);
CreateRMQ();
for (int i = 1; i <= m; i++)
{
fin >> n1 >> n2;
fout << querry(node[n1].firstPos, node[n2].firstPos) << '\n';
}
return 0;
}