using
System;
using
System.Collections.Generic;
class
GFG
{
static
readonly
int
MAXN = 100000;
static
readonly
int
level = 18;
static
List<
int
>[] tree =
new
List<
int
>[MAXN];
static
int
[] depth =
new
int
[MAXN];
static
int
[,] parent =
new
int
[MAXN, level];
static
void
dfs(
int
cur,
int
prev)
{
depth[cur] = depth[prev] + 1;
parent[cur,0] = prev;
for
(
int
i = 0; i < tree[cur].Count; i++)
{
if
(tree[cur][i] != prev)
dfs(tree[cur][i], cur);
}
}
static
void
precomputeSparseMatrix(
int
n)
{
for
(
int
i = 1; i < level; i++)
{
for
(
int
node = 1; node <= n; node++)
{
if
(parent[node, i - 1] != -1)
parent[node, i] = parent[parent[node, i - 1], i - 1];
}
}
}
static
int
lca(
int
u,
int
v)
{
if
(depth[v] < depth[u])
{
u = u + v;
v = u - v;
u = u - v;
}
int
diff = depth[v] - depth[u];
for
(
int
i = 0; i < level; i++)
if
(((diff >> i) & 1) == 1)
v = parent[v, i];
if
(u == v)
return
u;
for
(
int
i = level - 1; i >= 0; i--)
if
(parent[u, i] != parent[v, i])
{
u = parent[u, i];
v = parent[v, i];
}
return
parent[u, 0];
}
static
void
addEdge(
int
u,
int
v)
{
tree[u].Add(v);
tree[v].Add(u);
}
static
void
memset(
int
value)
{
for
(
int
i = 0; i < MAXN; i++)
{
for
(
int
j = 0; j < level; j++)
{
parent[i, j] = -1;
}
}
}
public
static
void
Main(String[] args)
{
memset(-1);
for
(
int
i = 0; i < MAXN; i++)
tree[i] =
new
List<
int
>();
int
n = 8;
addEdge(1, 2);
addEdge(1, 3);
addEdge(2, 4);
addEdge(2, 5);
addEdge(2, 6);
addEdge(3, 7);
addEdge(3, 8);
depth[0] = 0;
dfs(1, 0);
precomputeSparseMatrix(n);
Console.Write(
"LCA(4, 7) = "
+ lca(4, 7) +
"\n"
);
Console.Write(
"LCA(4, 6) = "
+ lca(4, 6) +
"\n"
);
}
}