LCA倍增算法模版
#include <iostream>
#include <cstring>
#include <cstdio>
#include <cmath>
#include <algorithm>
#include <vector>
using namespace std;
const int MaxN = 1e5;
int n, m;
int depth[MaxN + 1];
int f[MaxN + 1][20];
vector<int> g[MaxN + 1];
void dfs(int u, int fa, int deep)
{
depth[u] = deep;
for (int i = 0; i < g[u].size(); i++)
{
int v = g[u][i];
if (v == fa)
continue;
f[v][0] = u;
dfs(v, u, deep + 1);
}
}
void init()
{
for (int j = 1; (1 << j) <= n; j++)
for (int i = 1; i <= n; i++)
f[i][j] = f[f[i][j - 1]][j - 1];
}
int lca(int a, int b)
{
if (depth[a] < depth[b])
swap(a, b);
int d = depth[a] - depth[b];
for (int i = 0; d; d >>= 1, i++)
if (d & 1)
a = f[a][i];
if (a == b)
return a;
for (int i = 19; i >= 0; i--)
if (f[a][i] != f[b][i])
{
a = f[a][i];
b = f[b][i];
}
return f[a][0];
}
int dist(int x, int y)
{
return depth[x] + depth[y] - 2 * depth[lca(x, y)];
}
int main()
{
cin >> n >> m;
for (int i = 2; i <= n; i++)
{
int x;
scanf("%d", &x);
g[x].push_back(i);
g[i].push_back(x);
}
dfs(1, 0, 0);
init();
while (m--)
{
int a, b, c;
scanf("%d %d %d", &a, &b, &c);
int l1 = lca(a, b);
int l2 = lca(b, c);
int l3 = lca(a, c);
if (depth[l1] < depth[l2])
l1 = l2;
if (depth[l1] < depth[l3])
l1 = l3;
printf("%d\n", max(dist(l1, a), max(dist(l1, b), dist(l1, c))) + 1);
}
return 0;
}