学习算法——最近公共祖先
算法介绍:LCA(Least Common Ancestors),即最近公共祖先,是指在有根树中,找出某两个结点u和v最近的公共祖先。 ———来自百度百科
例题:洛谷-LCA模板题
模板代码:
#include <bits/stdc++.h>
using namespace std;
#define ll long long
const int maxn = 500005;
struct node{
int t,nex;
};
node a[maxn<<1];
int head[maxn],tot;
void add(int x,int y){
a[++tot].t = y,a[tot].nex = head[x],head[x] = tot;
}
int depth[maxn],fa[maxn][30],lg[maxn];
void dfs(int x,int fath)
{
fa[x][0] = fath,depth[x] = depth[fath] + 1;
for(int i=1;i<=lg[depth[x]];i++)
fa[x][i] = fa[fa[x][i-1]][i-1];
for(int i=head[x] ; i ; i = a[i].nex)
if(a[i].t != fath)
dfs(a[i].t , x);
}
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,s;
scanf("%d%d%d",&n,&m,&s);
for(int i=1;i<n;i++)
{
int x,y;
scanf("%d%d",&x,&y);
add(x,y),add(y,x);
}
for(int i=1;i<=n;i++)
lg[i] = lg[i-1] + (1<<lg[i-1] == i);
dfs(s , 0);
for(int i=1;i<=m;i++){
int x,y;
scanf("%d%d",&x,&y);
printf("%d\n",lca(x,y));
}
return 0;
}
京公网安备 11010502036488号