zoukankan      html  css  js  c++  java
  • bzoj 1787 紧急集合

    题目大意:

    一棵树上,两个相邻点之间距离为1,每次询问三个点,

    求到这三个点距离和最小的点,以及这个距离和

    思路:

    几乎是lca裸题

    lca:倍增即可

    然后求出每两个点之间的lca

    画画图可知必有两个lca相等

    而此时答案即为另一个lca

     1 #include<iostream>
     2 #include<cstdio>
     3 #include<algorithm>
     4 #include<cmath>
     5 #include<cstring>
     6 #include<cstdlib>
     7 #include<set>
     8 #include<map>
     9 #include<vector>
    10 #include<stack>
    11 #include<queue>
    12 #define ll long long
    13 #define inf 2147383611
    14 #define MAXN 1000101
    15 using namespace std;
    16 inline ll read()
    17 {
    18     ll x=0,f=1;
    19     char ch;ch=getchar();
    20     while(!isdigit(ch)) {if(ch=='-') f=-1;ch=getchar();}
    21     while(isdigit(ch)) {x=x*10+ch-'0';ch=getchar();}
    22     return x*f;
    23 }
    24 int cnt,n,T,to[MAXN],first[MAXN],next[MAXN];
    25 int depth[MAXN];
    26 int f[MAXN][28];
    27 void add(int u,int v) {next[++cnt]=first[u],first[u]=cnt,to[cnt]=v;}
    28 void dfs(int x,int fa)
    29 {
    30     for(int i=1;i<=25;i++)
    31     {
    32         if((1<<i)>=depth[x]) break;
    33         f[x][i]=f[f[x][i-1]][i-1];
    34     }
    35     for(int i=first[x];i;i=next[i]) if(to[i]!=fa) {depth[to[i]]=depth[x]+1;f[to[i]][0]=x;dfs(to[i],x);}
    36 }
    37 int lca(int u,int v)
    38 {
    39     if(depth[u]<depth[v]) swap(u,v);
    40     int d=depth[u]-depth[v];
    41     for(int i=25;i>=0;i--)
    42         if(d&(1<<i)) u=f[u][i];
    43     for(int i=25;i>=0;i--)
    44     {
    45         if(f[u][i]!=f[v][i]) u=f[u][i],v=f[v][i];
    46     }
    47     if(u==v) return v;
    48     return f[u][0];
    49 }
    50 int main()
    51 {
    52     n=read(),T=read();
    53     int a,b,c,l1,l2,l3;
    54     for(int i=1;i<n;i++) {a=read(),b=read();add(a,b);add(b,a);}
    55     depth[1]=1;dfs(1,0);
    56     while(T--)
    57     {
    58         a=read(),b=read(),c=read();
    59         l1=lca(a,b),l2=lca(a,c),l3=lca(b,c);
    60         if(l1==l2) printf("%d %d
    ",l3,depth[b]+depth[c]-depth[l3]*2+depth[a]-depth[l1]+depth[l3]-depth[l1]);
    61         else if(l1==l3) printf("%d %d
    ",l2,depth[a]+depth[c]-depth[l2]*2+depth[b]-depth[l1]+depth[l2]-depth[l1]);
    62         else if(l2==l3) printf("%d %d
    ",l1,depth[a]+depth[b]-depth[l1]*2+depth[c]-depth[l2]+depth[l1]-depth[l2]);
    63     }
    64 }
    View Code
  • 相关阅读:
    记一次与用户的亲密接触
    拨开障目的叶,一览CMDB庐山真面目
    广通软件获“2016年度中国最具影响力IT运维管理软件提供商”殊荣
    CMDB三大绝招,助我站稳运维之巅
    datetime module总结
    Python time module总结
    IPMItool小结
    Python selenium 延时的几种方法
    Python 字典操作
    YUM 配置
  • 原文地址:https://www.cnblogs.com/yyc-jack-0920/p/7602729.html
Copyright © 2011-2022 走看看