• Tarjan求LCA(离线)


    基本思想

    把要求的点对保存下来,在dfs时顺带求出来。

    方法

    将每个已经遍历的点指向它回溯的最高节点(遍历它的子树时指向自己),
    每遍历到一个点就处理它存在的询问
    如果另一个点已经遍历,则lca就是另一个点指向的点。否则跳过

    例如在下图中询问4,5和4,3的lca,遍历顺序为1,2,4,5,3

    遍历到4时,各个点的指向如图

    处理询问4,5和4,3。发现3和5没有遍历,跳过

    回溯到3,然后遍历5。

    发现4遍历过了,4,5的lca为2

    然后回溯到1,遍历3

    发现4遍历过了,4,3的lca为1

    具体每个点的指向可以用并查集实现,每个询问可以用邻接表存储

    具体实现

     P3379 【模板】最近公共祖先(LCA)

    #include<cstdio>
    #define maxn 500005
    struct Edge{
        int next,to;
    }edge[maxn*2],q[maxn*2];
    int n,m,fi[maxn],se,qi[maxn],sq=1,find[maxn],lca[maxn];
    bool vis[maxn];
    inline void add_edge(int u,int v){
        edge[++se].next=fi[u],edge[se].to=v,fi[u]=se,
        edge[++se].next=fi[v],edge[se].to=u,fi[v]=se;
    }
    inline void add_q(int u,int v){
        q[++sq].next=qi[u],q[sq].to=v,qi[u]=sq,
        q[++sq].next=qi[v],q[sq].to=u,qi[v]=sq;
    }
    int search(int x){//查找x指向的节点 
        if(find[x]==x)return x;
        return find[x]=search(find[x]);
    }
    void Tarjan(int x,int f){//Tarjan求LCA 
        find[x]=x,vis[x]=1;//当前节点已经遍历,并指向自己 
        for(int i=fi[x];i;i=edge[i].next){
            int v=edge[i].to;
            if(v==f)continue;
            Tarjan(v,x);
        }
        for(int i=qi[x];i;i=q[i].next){
            int v=q[i].to;
            if(vis[v])lca[i>>1]=search(v);//如果询问的另一个点已经遍历过,则LCA=search(v) 
        }
        find[x]=f;//当前节点及子树指向父亲 
    }
    int main(){
        int u,v,s;
        scanf("%d%d%d",&n,&m,&s);
        for(int i=1;i<n;i++){
            scanf("%d%d",&u,&v);
            add_edge(u,v);
        }
        for(int i=0;i<m;i++){
            scanf("%d%d",&u,&v);
            add_q(u,v);//将询问用邻接表存储 
        }
        Tarjan(s,0); 
        for(int i=1;i<=m;i++)printf("%d
    ",lca[i]);
        return 0;
    } 
  • 相关阅读:
    tool button 工具按钮
    push button 交替输出
    信号和槽
    qt新建一个工程
    lambda表达式
    横向滚动插件
    jquery循环延迟加载,用于在图片加载完成后再加载js
    dedecms的特性-----不完整
    让边框和文本一样高,不受line-height影响,可以使用padding,padding可以用于行内元素
    行内元素的行高对布局也有影响
  • 原文地址:https://www.cnblogs.com/bennettz/p/7985392.html
Copyright © 2020-2023  润新知