树链剖分求LCA板子

时间复杂度O(n+mlogn)

vector<int>e[maxn];
int fa[maxn],dep[maxn],son[maxn],sz[maxn];
//  存u的父节点,存u的深度,存u的重儿子,存以u为根的子树的节点数 
int top[maxn];
// 存u所在重链的顶点 
void dfs1(int u,int father){
	fa[u]=father,dep[u]=dep[father]+1,sz[u]=1;
	for(int v:e[u]){
		if(v==father)continue;
		dfs1(v,u);
		sz[u]+=sz[v];
		if(sz[son[u]]<sz[v]){
			son[u]=v;
		}
	}
}
void dfs2(int u,int t){
	top[u]=t;
	if(!son[u])return;//遇到叶子节点返回 
	dfs2(son[u],t);//向下搜重儿子
	for(int v:e[u]){
		if(v==fa[u]||v==son[u])continue;
		dfs2(v,v);//搜轻儿子 
	} 
}
int lca(int u,int v){
	while(top[u]!=top[v]){
		if(dep[top[u]]<dep[top[v]])swap(u,v);
		u=fa[top[u]];
	}
	return dep[u]<dep[v]?u:v;
}
posted @ 2025-03-12 20:34  Marinaco  阅读(2)  评论(0)    收藏  举报
//雪花飘落效果