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];
}
上一篇: c++的栈stack
下一篇: 【模板】最长公共子序列