• hdu 2586 How far away ? 倍增求LCA


    倍增求LCA

    LCA函数返回(u,v)两点的最近公共祖先

    #include <bits/stdc++.h>
    using namespace std;
    
    const int N = 40010*2;
    struct node {
        int v,val,next;
        node(){}
        node(int vv,int va,int nn):v(vv),val(va),next(nn){}
    }E[N];
    int n,m;
    int tot,head[N],dis[N],f[N][20],dep[N];
    
    void init() {
        tot = 0;
        memset(head,0,sizeof(head));
        memset(dis,0,sizeof(dis));
        memset(f,0,sizeof(f));
        memset(dep,0,sizeof(dep));
    }
    
    void add(int u,int v,int val) {
        E[++tot].next = head[u];
        E[tot].v = v;
        E[tot].val = val;
        head[u] = tot;
    }
    
    void addEdge(int u,int v,int val) {
        add(u,v,val);
        add(v,u,val);
    }
    
    void dfs(int x,int fa) {
        f[x][0] = fa;
        for(int i=1;f[x][i-1];i++)
            f[x][i] = f[f[x][i-1]][i-1];
        for(int i=head[x]; i; i=E[i].next) {
            int v = E[i].v;
            if(v != fa) {
                dis[v] = dis[x] + E[i].val;
                dep[v] = dep[x] + 1;
                dfs(v,x);
            }
        }
    }
    
    int lca(int u,int v) {
        if(dep[u] < dep[v]) swap(u,v);
        //int ans = dep[u] - dep[v];
        for(int i=19;i>=0;i--)
            if(dep[u]-(1<<i)>=dep[v])
                u = f[u][i];
        for(int i=19;i>=0;i--) {
            if(f[u][i]!=f[v][i])
                u=f[u][i],v=f[v][i];//ans+=(2<<i);
        }
        //if(u!=v) ans+=2;
        //return ans;
        if(u!=v) return f[u][0];
        else return u;
    }
    
    int main () {
        //freopen("in.txt","r",stdin);
        int T; scanf("%d",&T);
        while (T--) {
            init();
            scanf("%d %d",&n, &m);
            for(int i=1;i<=n-1;i++) {
                int u,v,val;
                scanf("%d %d %d",&u,&v,&val);
                addEdge(u,v,val);
            }
            dfs(1,0);
            // cout <<"yes" <<endl;
            while(m--) {
                int u,v; scanf("%d %d",&u,&v);
                int  t = lca(u,v);
                printf("%d
    ",dis[u]+dis[v]-2*dis[t]);
            }
        }
        return 0;
    }
  • 相关阅读:
    查找算法
    Android IPC
    运输层和TCP/IP协议
    二叉树的学习笔记
    java 和 JVM
    转载: GIt远程操作详解
    java-jpa-criteriaBuilder使用
    java项目构建工具Maven
    虚拟机下安装Maven
    validate表单验证-单独验证
  • 原文地址:https://www.cnblogs.com/Draymonder/p/9617303.html
Copyright © 2020-2023  润新知