/*
先来个倍增
*/
#include<iostream>
#include<cstring>
#include<cstdio>
#define maxn 10010
using namespace std;
int T,n,num,head[maxn],st,end,anc,fa[maxn][25],dep[maxn],out[maxn],root;
struct node
{int u,v,t,pre;
}e[maxn*2];
void Add(int from,int to)
{num++;e[num].u=from;e[num].v=to;e[num].pre=head[from];head[from]=num;
}
void Dfs(int now,int from,int c)
{fa[now][0]=from;dep[now]=c;for(int i=head[now];i;i=e[i].pre)if(e[i].v!=from)Dfs(e[i].v,now,c+1);
}
void Get_fa()
{for(int j=1;j<=16;j++)for(int i=1;i<=n;i++)fa[i][j]=fa[fa[i][j-1]][j-1];
}
int Get_same(int a,int t)
{for(int i=1;i<=t;i++)a=fa[a][0];return a;
}
int LCA(int a,int b)
{if(dep[a]<dep[b])swap(a,b);a=Get_same(a,dep[a]-dep[b]);if(a==b)return a;for(int i=16;i>=0;i--)if(fa[a][i]!=fa[b][i]){a=fa[a][i];b=fa[b][i];}return fa[a][0];
}
int main()
{scanf("%d",&T);while(T--){memset(head,0,sizeof(head));memset(fa,0,sizeof(fa)); memset(out,0,sizeof(out));memset(dep,0,sizeof(dep));num=0;root=0;scanf("%d",&n);int x,y;for(int i=1;i<=n-1;i++){scanf("%d%d",&x,&y);Add(x,y);Add(y,x);out[y]=1;}for(int i=1;i<=n;i++)if(out[i]==0)root=i;Dfs(root,root,0);Get_fa();scanf("%d%d",&st,&end);anc=LCA(st,end);printf("%d\n",anc);}return 0;
}

/*
离线Tarjan
我们Dfs整张图的时候 对于一组u v
我们一定按照 u s v 的顺序跑完
此时u v 在以s为根的子树里
那么我们借助并茶几 将u v的fa 的anc赋值为s
这样我们查询u v 的时候就能找到s
如果我们求 st end 的lca
当我们遍历到st 或者end的时候 只需要判断另一个是不是已经被访问过
*/
#include<iostream>
#include<cstdio>
#include<cstring>
#include<vector>
#define maxn 100010
using namespace std;
int T,n,m,fa[maxn],st,end,anc[maxn];
vector<int>a[maxn];
int root[maxn],f[maxn];
void init()
{scanf("%d",&n);int x,y;for(int i=1;i<=n;i++){fa[i]=i;root[i]=1;}for(int i=1;i<=n-1;i++){scanf("%d%d",&x,&y);a[x].push_back(y);fa[y]=x;root[y]=0;}
}
int find(int x)
{if(x!=fa[x])fa[x]=find(fa[x]);return fa[x];
}
void Union(int x,int y)
{int r1=find(x);int r2=find(y);if(r1!=r2)fa[r2]=r1;
}
void LCA(int parent)
{anc[parent]=parent;//初始化自己的lca为自己 for(int i=0;i<a[parent].size();i++){LCA(a[parent][i]);Union(parent,a[parent][i]);anc[find(parent)]=parent;//把自己和自己子孙们的lca赋值为它
      }f[parent]=1;if(st==parent&&f[end]==1){printf("%d\n",anc[find(end)]);return;}if(end==parent&&f[st]==1){printf("%d\n",anc[find(st)]);return;}
}
int main()
{scanf("%d",&T);while(T--){memset(f,0,sizeof(f));memset(a,0,sizeof(a));init();scanf("%d%d",&st,&end);for(int i=1;i<=n;i++)if(root[i])LCA(i);}return 0;
}

转载于:https://www.cnblogs.com/yanlifneg/p/5546115.html

poj 1330 LCA (倍增+离线Tarjan)相关推荐

  1. POJ 1330 LCA最近公共祖先 离线tarjan算法

    题意要求一棵树上,两个点的最近公共祖先 即LCA 现学了一下LCA-Tarjan算法,还挺好理解的,这是个离线的算法,先把询问存贮起来,在一遍dfs过程中,找到了对应的询问点,即可输出 原理用了并查集 ...

  2. 01分数规划c语言,POJ 1330(LCA/倍增法模板)

    链接:http://poj.org/problem?id=1330 题意:q次询问求两个点u,v的LCA 思路:LCA模板题,首先找一下树的根,然后dfs预处理求LCA(u,v) AC代码: #inc ...

  3. poj 3728 The merchant// lca(倍增实现) + dp || tarjan+并查集路径上dp

    poj 3728 The merchant// lca(倍增实现) + dp Time Limit: 3000MS   Memory Limit: 65536K Total Submissions: ...

  4. POJ 1330 Nearest Common Ancestors / UVALive 2525 Nearest Common Ancestors (最近公共祖先LCA)...

    POJ 1330 Nearest Common Ancestors / UVALive 2525 Nearest Common Ancestors (最近公共祖先LCA) Description A ...

  5. LCA(倍增+Tarjan)和BFS、DFS以及Prim、Kruskal

    文章目录 LCA 倍增 并查集 题目背景 题目描述 输入格式 输出格式 输入输出样例 Tarjan算法 LCA和倍增 LCA和Tarjan 深度优先搜索 广搜BFS 最小生成树 普里姆算法(找点) 克 ...

  6. LCA倍增法 求树的最近公共祖先(模板)

    LCA倍增法 求树的最近公共祖先 查询树上任意两个节点之间的路径信息,实际上就是找这两个节点的LCA,因为唯一路径就是这两个节点分别到LCA会合,所以关键问题就是求LCA,需要的路径信息可在找LCA过 ...

  7. hdu 2586(LCA的离线做法)

    lca上的tarjan,改了我一下午加一晚上的bug,还无奈重写了一次.就是寻找最近公共祖先lca(u,v #include <iostream> #include <cstring ...

  8. POJ 1470 Closest Common Ancestors (最近公共祖先LCA 的离线算法Tarjan)

    Tarjan算法的详细介绍,请戳: http://www.cnblogs.com/chenxiwenruo/p/3529533.html #include <iostream> #incl ...

  9. POJ - 1330 Nearest Common Ancestors(树上倍增/树链剖分求LCA)

    题目链接:点击查看 题目大意:给出一棵有根树,我们需要求出两个点的lca 题目分析:因为题目说了是有根树,所以我们在建图的时候直接建有向图就好了,并且记录一下每个点的入度,建完图后找一下入度为0的点, ...

最新文章

  1. 【网络安全】域渗透之完全绕开安全组件
  2. BOOST_LOG_UNIQUE_IDENTIFIER_NAME宏用法的测试程序
  3. GDCM:获取dicom文件Sequence的长度的测试程序
  4. MAC地址如何在windows与unix下查看?
  5. 理解JWT(JSON Web Token)认证及python实践
  6. 如果在iTerm2中复制命令特别卡,就跟慢动作似的,怎么办?
  7. 使用 gunicorn 部署flask项目
  8. mysql给指定数据增加前后缀update,替换replace字段值
  9. kafka告警简单方案
  10. Theano 中文文档 0.9 - 4. 要求
  11. javascript篇:策略模式验证表单
  12. mysql-connector-java-5.1.22下载
  13. Arcgis之国土报备(征地Xls)Xls格式批量转shp格式工具
  14. CAD2007 病毒 处理办法
  15. 【备忘录】UTM坐标系与经纬度转换 MATLAB C语言
  16. 安立与ETS-Lindgren联合发布天线测量软件的增强解决方案
  17. provisional headers are shown
  18. 【回归预测-ELM预测】基于遗传算法优化极限学习机实现风电数据回归预测附matlab代码
  19. 无法加载计算机管理,电脑中无法打开Internet选项中的管理加载项如何解决
  20. RE:Working outside of application context

热门文章

  1. 写给粪坑里的钻石——烂公司里的好员工
  2. 今天开始写技术博客啦
  3. 虹康三期倒垃圾时间和理发地点
  4. idea maven 出现:Try-with-resources are not supported at language level ‘5‘
  5. No ExecutorFactory found to execute the application
  6. 2019年查询12年前的往届高考成绩(适用浙江省)
  7. NIFI的ERROR报错信息如何清空
  8. intellij2018修改代码背景颜色
  9. 7.4.1 矩阵低秩近似、矩阵范数
  10. java 缘起_GraalVM 助力 Java 进入函数即服务时代