luogu P3379 LCA
题目链接
传送门
#include <bits/stdc++.h>
using namespace std;
const int N = 5e5 + 10;
int nxt[N<<1],head[N],to[N<<1],tot;
void add(int u,int v)
{
nxt[++tot] = head[u];
head[u] = tot;
to[tot] = v;
}
int depth[N],fa[N][23],lg[N];
void dfs(int u,int fath)
{
fa[u][0] = fath;
depth[u] = depth[fath] + 1;
for(int i=1;i<=lg[depth[u]];i++)
{
fa[u][i] = fa[fa[u][i-1]][i-1];
}
for(int i=head[u];i;i=nxt[i])
{
if(to[i]!=fath)
dfs(to[i],u);
}
}
int LCA(int x,int y)
{
if(depth[x]<depth[y])
swap(x,y);
while(depth[x]>depth[y])
{
x = fa[x][lg[depth[x]-depth[y]]-1];
}
if(x==y)
return x;
for(int k=lg[depth[x]]-1;k>=0;k--)
{
if(fa[x][k]!=fa[y][k])
x = fa[x][k],y = fa[y][k];
}
return fa[x][0];
}
int main() {
int n,m,start;
scanf("%d%d%d",&n,&m,&start);
for(int i=1;i<=n-1;i++)
{
int u,v;
scanf("%d%d",&u,&v);
add(u,v);
add(v,u);
}
for(int i=1;i<=n;i++)
{
lg[i] = lg[i-1] + (1 << lg[i-1] == i);
}
dfs(start,0);
for(int i=1;i<=m;i++)
{
int x,y;
scanf("%d%d",&x,&y);
printf("%d\n",LCA(x,y));
}
return 0;
}