Pagini recente » Cod sursa (job #228361) | Cod sursa (job #2943547) | Cod sursa (job #892173) | Cod sursa (job #2404611) | Cod sursa (job #3140107)
#include <fstream>
#define nmx 100005
#include <vector>
using namespace std;
int n,m,x,euler[4*nmx],lvl[4*nmx],firstp[4*nmx],log[2*nmx],dp[20][4*nmx];
vector <int> child[nmx];
void eul(int nod,int niv,int &ct)
{
euler[++ct]=nod;
lvl[ct]=niv;
firstp[nod]=ct;
for (auto it : child[nod])
{
eul(it,niv+1,ct);
euler[++ct]=nod;
lvl[ct]=niv;
}
}
void rmq(int k)
{
log[1]=0;
for (int i=2; i<=k; i++)
log[i]=log[i/2]+1;
for (int i=1; i<=k; i++)
dp[0][i]=i;
for (int i=1; (1<<i)<=k; i++)
for (int j=1; j<=k-(1<<i)+1; j++)
{
int pw=1<<(i-1);
if (lvl[dp[i-1][j]]<lvl[dp[i-1][j+pw]])
dp[i][j]=dp[i-1][j];
else
dp[i][j]=dp[i-1][j+pw];
}
}
int lca(int a,int b)
{
if (a>b) swap(a,b);
int dif=b-a+1;
int lg=log[dif];
int pw=(1<<lg);
if (lvl[dp[lg][a]]<lvl[dp[lg][b-pw+1]])
return euler[dp[lg][a]];
return euler[dp[lg][b-pw+1]];
}
int main()
{
ifstream f("lca.in");
ofstream g("lca.out");
f>>n>>m;
for (int i=2; i<=n; i++)
{
f>>x;
child[x].push_back(i);
}
int c=0;
eul(1,0,c);
rmq(c);
int a,b;
for (int i=1;i<=m;i++)
{
f>>a>>b;
g<<lca(firstp[a],firstp[b])<<'\n';
}
}