欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

st表求lca

程序员文章站 2024-01-14 16:53:10
...

对于st表求lca可以做到O(1)查询。

对于一个欧拉序,每个点对应其第一次出现在欧拉序中的位置。

然后查询区间dep的最小值,这是st表干的。

完了。

void dfs(int u,int faa){
		dep[u]=dep[faa]+1;fa[u][0]=faa;dfn[u]=++cntdfn;
		fir[u]=++cntt;st[0][cntt]=u;
		for(int i=1;i<=18;i++)fa[u][i]=fa[fa[u][i-1]][i-1];
		for(int i=first[u];i;i=nxt[i]){
			int v=to[i];if(v==faa)continue;
			dfs(v,u);st[0][++cntt]=u;
		}
	}
	void prepare(){
		lg[0]=-1;for(int i=1;i<=N*2;i++)lg[i]=lg[i>>1]+1;
		for(int i=1;i<=17;i++){
			for(int j=1;j+(1<<i)-1<=cntt;j++){
				st[i][j]=dep[st[i-1][j]]<dep[st[i-1][j+(1<<(i-1))]]?st[i-1][j]:st[i-1][j+(1<<(i-1))];
			}
		}
	}
	int Lca(int a,int b){
		int l=fir[a],r=fir[b],k;
		if(l>r)swap(l,r);
		k=lg[r-l+1];
		return dep[st[k][l]]<dep[st[k][r-(1<<k)+1]]?st[k][l]:st[k][r-(1<<k)+1];
	}