• lca 欧拉序+rmq(st) 欧拉序+rmq(线段树) 离线dfs 倍增


    https://www.luogu.org/problemnew/show/P3379

    1.欧拉序+rmq(st)

      1 /*
      2 在这里,对于一个数,选择最左边的
      3 选择任意一个都可以,[left_index,right_index],深度都大于等于这个数的深度
      4 */
      5 #include <cstdio>
      6 #include <cstdlib>
      7 #include <cmath>
      8 #include <cstring>
      9 #include <time.h>
     10 #include <string>
     11 #include <set>
     12 #include <map>
     13 #include <list>
     14 #include <stack>
     15 #include <queue>
     16 #include <vector>
     17 #include <bitset>
     18 #include <ext/rope>
     19 #include <algorithm>
     20 #include <iostream>
     21 using namespace std;
     22 #define ll long long
     23 #define minv 1e-6
     24 #define inf 1e9
     25 #define pi 3.1415926536
     26 #define E  2.7182818284
     27 const ll mod=1e9+7;//998244353
     28 const int maxn=5e5+10;
     29 
     30 struct node
     31 {
     32     int d;
     33     node *next;
     34 }*e[maxn];
     35 
     36 int s=0;
     37 
     38 ///每条边走两遍,n-1条边,走2(n-1)个点
     39 int a[maxn<<1],b[maxn<<1],f[maxn<<1][20],lef[maxn],er[20];
     40 bool vis[maxn]={0};
     41 
     42 void dfs(int d,int dep)
     43 {
     44     node* p=e[d];
     45     vis[d]=1;
     46     s++;
     47     lef[d]=s;
     48     a[s]=d;
     49     b[s]=dep;
     50     while (p)
     51     {
     52         if (!vis[p->d])
     53         {
     54             dfs(p->d,dep+1);
     55             s++;
     56             a[s]=d;
     57             b[s]=dep;
     58         }
     59         p=p->next;
     60     }
     61 }
     62 
     63 int main()
     64 {
     65     int n,q,root,x,y,i,j,k,m,d;
     66     node *p;
     67     scanf("%d%d%d",&n,&q,&root);
     68     for (i=1;i<n;i++)
     69     {
     70         scanf("%d%d",&x,&y);
     71         p=(node*) malloc (sizeof(node));
     72         p->d=y;
     73         p->next=e[x];
     74         e[x]=p;
     75 
     76         p=(node*) malloc (sizeof(node));
     77         p->d=x;
     78         p->next=e[y];
     79         e[y]=p;
     80     }
     81     dfs(root,1);
     82 
     83     m=log(s)/log(2);
     84     er[0]=1;
     85     for (i=1;i<=m;i++)
     86         er[i]=er[i-1]<<1;
     87     for (i=1;i<=s;i++)
     88         f[i][0]=i;
     89 //        f[i][0]=b[i];
     90     for (i=1;i<=m;i++)   //2^i
     91         for (j=1,k=j+er[i-1];j<=s-er[i]+1;j++,k++)  //-er[i]+1
     92             if (b[ f[j][i-1] ] < b[ f[k][i-1] ])
     93                 f[j][i]=f[j][i-1];
     94             else
     95                 f[j][i]=f[k][i-1];
     96 //            f[j][i]=min(f[j][i-1],f[j+er[i-1]][i-1]);
     97 
     98     while (q--)
     99     {
    100         scanf("%d%d",&x,&y);
    101         x=lef[x];
    102         y=lef[y];
    103         if (x>y)
    104             swap(x,y);
    105         d=log(y-x+1)/log(2);
    106         j=y-er[d]+1;
    107         if (b[ f[x][d] ] < b[ f[j][d] ])    //+1
    108             printf("%d
    ",a[ f[x][d] ]);
    109         else
    110             printf("%d
    ",a[ f[j][d] ]);
    111 //        printf("%d
    ",min(f[x][d],f[y-er[d]+1][d]));
    112     }
    113     return 0;
    114 }
    115 /*
    116 8 100 1
    117 1 2
    118 1 3
    119 2 4
    120 2 5
    121 3 6
    122 5 7
    123 6 8
    124 
    125 5 7
    126 5
    127 2 3
    128 1
    129 3 2
    130 1
    131 1 8
    132 1
    133 2 8
    134 1
    135 4 5
    136 2
    137 5 4
    138 2
    139 */

    2.欧拉序+线段树

      1 /*
      2 在这里,对于一个数,选择最左边的
      3 选择任意一个都可以,[left_index,right_index],深度都大于等于这个数的深度
      4 */
      5 #include <cstdio>
      6 #include <cstdlib>
      7 #include <cmath>
      8 #include <cstring>
      9 #include <time.h>
     10 #include <string>
     11 #include <set>
     12 #include <map>
     13 #include <list>
     14 #include <stack>
     15 #include <queue>
     16 #include <vector>
     17 #include <bitset>
     18 #include <ext/rope>
     19 #include <algorithm>
     20 #include <iostream>
     21 using namespace std;
     22 #define ll long long
     23 #define minv 1e-6
     24 #define inf 1e9
     25 #define pi 3.1415926536
     26 #define E  2.7182818284
     27 const ll mod=1e9+7;//998244353
     28 const int maxn=5e5+10;
     29 
     30 struct node
     31 {
     32     int d;
     33     node *next;
     34 }*e[maxn];
     35 
     36 int s=0;
     37 
     38 ///每条边走两遍,n-1条边,走2(n-1)个点
     39 int a[maxn<<1],b[maxn<<1],lef[maxn],f[maxn<<3];
     40 bool vis[maxn]={0};
     41 int num=0;
     42 
     43 void dfs(int d,int dep)
     44 {
     45     node* p=e[d];
     46     vis[d]=1;
     47     s++;
     48     lef[d]=s;
     49     a[s]=d;
     50     b[s]=dep;
     51     while (p)
     52     {
     53         if (!vis[p->d])
     54         {
     55             dfs(p->d,dep+1);
     56             s++;
     57             a[s]=d;
     58             b[s]=dep;
     59         }
     60         p=p->next;
     61     }
     62 }
     63 
     64 void build(int index,int l,int r)
     65 {
     66     if (l==r)
     67         f[index]=++num;
     68     else
     69     {
     70         int m=(l+r)>>1;
     71         build(index<<1,l,m);
     72         build(index<<1|1,m+1,r);
     73         if (b[f[index<<1]]<b[f[index<<1|1]])
     74             f[index]=f[index<<1];
     75         else
     76             f[index]=f[index<<1|1];
     77     }
     78 }
     79 
     80 int query(int index,int l,int r,int x,int y)
     81 {
     82     if (x<=l && r<=y)
     83         return f[index];
     84     if (r<x || l>y)
     85         return 0;
     86     int m=(l+r)>>1;
     87     int p=query(index<<1,l,m,x,y);
     88     int q=query(index<<1|1,m+1,r,x,y);
     89     if (b[p]<b[q])
     90         return p;
     91     else
     92         return q;
     93 }
     94 
     95 int main()
     96 {
     97     int n,q,root,x,y,i,j,m,d;
     98     node *p;
     99     scanf("%d%d%d",&n,&q,&root);
    100     for (i=1;i<n;i++)
    101     {
    102         scanf("%d%d",&x,&y);
    103         p=(node*) malloc (sizeof(node));
    104         p->d=y;
    105         p->next=e[x];
    106         e[x]=p;
    107 
    108         p=(node*) malloc (sizeof(node));
    109         p->d=x;
    110         p->next=e[y];
    111         e[y]=p;
    112     }
    113     dfs(root,1);
    114 
    115     b[0]=n+1;
    116     build(1,1,s);
    117     while (q--)
    118     {
    119         scanf("%d%d",&x,&y);
    120         x=lef[x];
    121         y=lef[y];
    122         if (x>y)
    123             swap(x,y);
    124         printf("%d
    ",a[query(1,1,s,x,y)]);
    125     }
    126     return 0;
    127 }

    3.离线dfs

      1 #include <cstdio>
      2 #include <cstdlib>
      3 #include <cmath>
      4 #include <cstring>
      5 #include <time.h>
      6 #include <string>
      7 #include <set>
      8 #include <map>
      9 #include <list>
     10 #include <stack>
     11 #include <queue>
     12 #include <vector>
     13 #include <bitset>
     14 #include <ext/rope>
     15 #include <algorithm>
     16 #include <iostream>
     17 using namespace std;
     18 #define ll long long
     19 #define minv 1e-6
     20 #define inf 1e9
     21 #define pi 3.1415926536
     22 #define E  2.7182818284
     23 const ll mod=1e9+7;//998244353
     24 const int maxn=5e5+10;
     25 
     26 struct node
     27 {
     28     int d;
     29     node *next;
     30 }*e[maxn];
     31 struct rec
     32 {
     33     int d,index;
     34     rec *next;
     35 }*ask[maxn];
     36 bool vis[maxn]={0};
     37 
     38 int r[maxn],fa[maxn];
     39 
     40 int getfather(int d)
     41 {
     42     if (fa[d]==d)
     43         return d;
     44     fa[d]=getfather(fa[d]);
     45     return fa[d];
     46 }
     47 
     48 void merge(int x,int y)
     49 {
     50     int s=getfather(x);
     51     int t=getfather(y);
     52     fa[t]=s;
     53 }
     54 
     55 void dfs(int d)
     56 {
     57     node *p;
     58     rec *v;
     59     vis[d]=1;
     60 
     61     p=e[d];
     62     while (p)
     63     {
     64         if (!vis[p->d])
     65         {
     66             dfs(p->d);
     67             merge(d,p->d);
     68         }
     69         p=p->next;
     70     }
     71 
     72     v=ask[d];
     73     while (v)
     74     {
     75         if (vis[v->d])
     76             r[v->index]=getfather(v->d);
     77         v=v->next;
     78     }
     79 }
     80 
     81 int main()
     82 {
     83     node *p;
     84     rec *v;
     85     int n,q,root,x,y,i;
     86     scanf("%d%d%d",&n,&q,&root);
     87     for (i=1;i<n;i++)
     88     {
     89         scanf("%d%d",&x,&y);
     90         p=(node*) malloc (sizeof(node));
     91         p->d=y;
     92         p->next=e[x];
     93         e[x]=p;
     94 
     95         p=(node*) malloc (sizeof(node));
     96         p->d=x;
     97         p->next=e[y];
     98         e[y]=p;
     99     }
    100 
    101     for (i=1;i<=q;i++)
    102     {
    103         scanf("%d%d",&x,&y);
    104         v=(rec*) malloc (sizeof(rec));
    105         v->d=y;
    106         v->index=i;
    107         v->next=ask[x];
    108         ask[x]=v;
    109 
    110         v=(rec*) malloc (sizeof(rec));
    111         v->d=x;
    112         v->index=i;
    113         v->next=ask[y];
    114         ask[y]=v;
    115     }
    116 
    117     for (i=1;i<=n;i++)
    118         fa[i]=i;
    119     dfs(root);
    120     for (i=1;i<=q;i++)
    121         printf("%d
    ",r[i]);
    122     return 0;
    123 }

    4.倍增

      1 #include <cstdio>
      2 #include <cstdlib>
      3 #include <cmath>
      4 #include <cstring>
      5 #include <time.h>
      6 #include <string>
      7 #include <set>
      8 #include <map>
      9 #include <list>
     10 #include <stack>
     11 #include <queue>
     12 #include <vector>
     13 #include <bitset>
     14 #include <ext/rope>
     15 #include <algorithm>
     16 #include <iostream>
     17 using namespace std;
     18 #define ll long long
     19 #define minv 1e-6
     20 #define inf 1e9
     21 #define pi 3.1415926536
     22 #define nl 2.7182818284
     23 const ll mod=1e9+7;//998244353
     24 const int maxn=5e5+10;
     25 
     26 struct node
     27 {
     28     int d;
     29     node *next;
     30 }*e[maxn];
     31 
     32 bool vis[maxn]={0};
     33 int q[maxn],dep[maxn],f[maxn][20];
     34 
     35 int main()
     36 {
     37     node *p;
     38     int n,Q,root,head,tail,x,y,d,dd,i,j,k;
     39     scanf("%d%d%d",&n,&Q,&root);
     40     for (i=1;i<n;i++)
     41     {
     42         scanf("%d%d",&x,&y);
     43         p=new node();
     44         p->d=y;
     45         p->next=e[x];
     46         e[x]=p;
     47 
     48         p=new node();
     49         p->d=x;
     50         p->next=e[y];
     51         e[y]=p;
     52     }
     53 
     54     head=0,tail=1;
     55     vis[root]=1;
     56     q[1]=root;
     57     dep[root]=0;
     58     while (head<tail)
     59     {
     60         head++;
     61         d=q[head];
     62         p=e[d];
     63         while (p)
     64         {
     65             dd=p->d;
     66             if (!vis[dd])
     67             {
     68                 tail++;
     69                 q[tail]=dd;
     70                 vis[dd]=1;
     71                 dep[dd]=dep[d]+1;
     72                 //f[dd][0]=d;
     73 
     74                 j=d;
     75                 k=0;
     76                 while (j)
     77                 {
     78                     f[dd][k]=j;
     79                     j=f[j][k];
     80                     k++;
     81                 }
     82             }
     83             p=p->next;
     84         }
     85     }
     86     while (Q--)
     87     {
     88         scanf("%d%d",&x,&y);
     89         if (dep[x]<dep[y])
     90             swap(x,y);
     91 
     92         i=dep[x]-dep[y];
     93         j=0;
     94         while (i)
     95         {
     96             if (i & 1)
     97                 x=f[x][j];
     98             i>>=1;
     99             j++;
    100         }
    101 
    102         if (dep[x]==0)
    103             k=0;
    104         else
    105             k=log(dep[x]+minv)/log(2)+1;
    106         i=(1<<k);
    107         while (k)
    108         {
    109             k--;
    110             i>>=1;
    111             if (dep[x]>=i && f[x][k]!=f[y][k])
    112             {
    113                 x=f[x][k];
    114                 y=f[y][k];
    115             }
    116         }
    117         if (x!=y)
    118             x=f[x][0];
    119         printf("%d
    ",x);
    120     }
    121     return 0;
    122 }
    123 /*
    124 5 100 1
    125 1 2
    126 2 3
    127 3 4
    128 4 5
    129 
    130 1 5
    131 3 4
    132 2 4
    133 2 5
    134 
    135 
    136 7 100 1
    137 1 2
    138 2 3
    139 2 4
    140 4 5
    141 4 6
    142 1 7
    143 
    144 5 7
    145 3 7
    146 5 1
    147 2 6
    148 3 6
    149 
    150 10 100 1
    151 1 2
    152 2 3
    153 3 4
    154 4 5
    155 5 6
    156 6 7
    157 7 8
    158 8 9
    159 9 10
    160 
    161 1 10
    162 2 10
    163 3 10
    164 4 10
    165 5 9
    166 7 8
    167 
    168 10 100 1
    169 1 2
    170 2 3
    171 3 4
    172 3 5
    173 5 6
    174 5 7
    175 2 8
    176 8 9
    177 9 10
    178 
    179 6 10
    180 4 10
    181 3 1
    182 6 7
    183 3 10
    184 2 10
    185 3 7
    186 6 7
    187 4 7
    188 
    189 
    190 10 100 1
    191 1 2
    192 1 3
    193 1 4
    194 3 5
    195 3 6
    196 3 7
    197 7 8
    198 7 9
    199 7 10
    200 
    201 15 100 1
    202 1 2
    203 2 3
    204 3 4
    205 4 5
    206 5 6
    207 6 7
    208 7 8
    209 8 9
    210 9 10
    211 10 11
    212 11 12
    213 12 13
    214 13 14
    215 14 15
    216 
    217 1 15
    218 2 15
    219 2 14
    220 3 14
    221 3 13
    222 4 13
    223 4 12
    224 
    225 
    226 12 100 1
    227 1 2
    228 2 3
    229 3 4
    230 4 5
    231 5 6
    232 1 7
    233 7 8
    234 8 9
    235 9 10
    236 10 11
    237 11 12
    238 
    239 6 12
    240 4 7
    241 8 12
    242 1 6
    243 */
  • 相关阅读:
    sql
    Java后台通过传参得到对应的坐标值的方法
    运行第一个大型项目工程时出现的问题
    对sqlserver存储过程合游标循环中的一点心得
    (基于Java)算法之动态规划——矩阵连乘问题
    算法之线性时间选择(最坏情况下)
    算法之快速排序
    算法之合并排序
    算法之二分搜索法
    设计模式之装饰者模式
  • 原文地址:https://www.cnblogs.com/cmyg/p/9545267.html
Copyright © 2020-2023  润新知