倍增求lca
/*
节点维护的信息多样
如果用树状数组维护到根节点的边权或者点权, 可以直接插入点权和边权值,不需要预处理,
但是记得一定要使用ot[]消除影响.即差分. Housewife Wind 这个坑踩得死死得.
然后如果带修改,也可以线段树维护.
打上dfs序后, 其他的就是区间问题了. 然后查询 修改的时候,把dfs序与点或者边对应转换一下就OK了.
*/
int deep[maxn];
int up[maxn][];
int in[maxn]; // dfs序 入
int ot[maxn]; // dfs序 出
int pa[maxn]; // father 数组
int qsz, qtot; // 预处理出 deep[] in[] ot[] pa[] up[i][0]
void dfs(int u, int fa)
{
int i, v;
deep[u] = deep[fa] + ;
in[u] = qtot;
for (i=head[u]; i; i=edge[i].lst) {
v = edge[i].to;
if (v == fa) continue;
up[v][] = u;
pa[v] = u;
++qtot; // dfs序标号用.
dfs(v, u);
}
ot[u] = qtot;
} // 获取公共祖先的表.
void GetUp(int n)
{
int i, j;
for (j=; j<; ++j)
for (i=; i<=n; ++i)
up[i][j] = up[up[i][j-]][j-];
} // 倍增求lca
int lca(int u, int v)
{
if (deep[u] < deep[v]) swap(u, v);
int i, j, k = deep[u] - deep[v];
for (i=; i<; ++i) // 获取第k个祖先
if ((<<i) & k)
u = up[u][i];
if (u != v) {
for (i=; i>=; --i)
if (up[u][i] != up[v][i]) {
u = up[u][i];
v = up[v][i];
}
u = up[u][];
}
return u;
} int main()
{
// 多Cas记得清零 up[][] 之类的数组 还有全局变量
deep[] = ;
dfs(, );
GetUp(n); // 在dfs()预处理出各节点的父亲后调用. return ;
}
至于求解答案的几种, 一般也就那几种, 根据维护的信息来画个图,看怎么求解答案.
倍增求lca的更多相关文章
- 树上倍增求LCA(最近公共祖先)
前几天做faebdc学长出的模拟题,第三题最后要倍增来优化,在学长的讲解下,尝试的学习和编了一下倍增求LCA(我能说我其他方法也大会吗?..) 倍增求LCA: father[i][j]表示节点i往上跳 ...
- [算法]树上倍增求LCA
LCA指的是最近公共祖先(Least Common Ancestors),如下图所示: 4和5的LCA就是2 那怎么求呢?最粗暴的方法就是先dfs一次,处理出每个点的深度 然后把深度更深的那一个点(4 ...
- 【倍增】洛谷P3379 倍增求LCA
题目描述 如题,给定一棵有根多叉树,请求出指定两个点直接最近的公共祖先. 输入输出格式 输入格式: 第一行包含三个正整数N.M.S,分别表示树的结点个数.询问的个数和树根结点的序号. 接下来N-1行每 ...
- hdu 2586 How far away ? 倍增求LCA
倍增求LCA LCA函数返回(u,v)两点的最近公共祖先 #include <bits/stdc++.h> using namespace std; *; struct node { in ...
- 倍增求lca模板
倍增求lca模板 https://www.luogu.org/problem/show?pid=3379 #include<cstdio> #include<iostream> ...
- 【题解】洛谷P4180 [BJWC2010] 严格次小生成树(最小生成树+倍增求LCA)
洛谷P4180:https://www.luogu.org/problemnew/show/P4180 前言 这可以说是本蒟蒻打过最长的代码了 思路 先求出此图中的最小生成树 权值为tot 我们称这棵 ...
- 倍增求LCA学习笔记(洛谷 P3379 【模板】最近公共祖先(LCA))
倍增求\(LCA\) 倍增基础 从字面意思理解,倍增就是"成倍增长". 一般地,此处的增长并非线性地翻倍,而是在预处理时处理长度为\(2^n(n\in \mathbb{N}^+)\ ...
- 树链剖分与倍增求LCA
树链剖分与倍增求\(LCA\) 首先我要吐槽机房的辣基供电情况,我之前写了一上午,马上就要完成的时候突然停电,然后\(GG\)成了送链剖分 其次,我没歧视\(tarjan LCA\) 1.倍增求\(L ...
- [学习笔记] 树上倍增求LCA
倍增这种东西,听起来挺高级,其实功能还没有线段树强大.线段树支持修改.查询,而倍增却不能支持修改,但是代码比线段树简单得多,而且当倍增这种思想被应用到树上时,它的价值就跟坐火箭一样,噌噌噌地往上涨. ...
- 树上倍增求LCA及例题
先瞎扯几句 树上倍增的经典应用是求两个节点的LCA 当然它的作用不仅限于求LCA,还可以维护节点的很多信息 求LCA的方法除了倍增之外,还有树链剖分.离线tarjan ,这两种日后再讲(众人:其实是你 ...
随机推荐
- free结果解释
free用于查询内存使用情况,不过其多个数值经常让人感到迷惑,下边对其结果各值进行解释. Mem 1862--总内存/1770--已使用内存/92--未使用内存/199--输出缓存/637--输入缓存 ...
- Linux几种服务用处介绍
rexec--Remote Execute,远程命令执行,允许远程机器在本机上远程执行命令,监听端口512. nfs--Network File System,网络文件系统,用于将本机文件夹共享到别的 ...
- 通过springboot 去创建和提交一个表单(七)
创建工程 涉及了 web,加上spring-boot-starter-web和spring-boot-starter-thymeleaf的起步依赖. 1 2 3 4 5 6 7 8 9 10 11 1 ...
- ajax常见的面试问题
1:什么是ajax?ajax作用是什么? 异步的javascript和xml AJAX 是一种用于创建快速动态网页的技术. ajax用来与后台交互 2:原生js ajax请求有几个步骤?分别是什么 / ...
- C/C++ 运算符优先级(转载)
最讨厌这个了.在这里记录下. 优先级 操作符 描述 例子 结合性 1 ()[]->.::++-- 调节优先级的括号操作符数组下标访问操作符通过指向对象的指针访问成员的操作符通过对象本身访问成员的 ...
- [IOS微信] Unicode码 转化为字符串
最近在研究IOS手机备份的数据,里面的微信数据中,每一个微信账号对应一个文件:mmsetting.archive 用来保存此账号的详细信息. 该文件是一个加强版的plist文件(此文件使用的是plis ...
- laravel5.2 开发中打印sql语句
在 AppServiceProvider 的boot方法中写入 use DB;use Event; if ( env('APP_ENV') == 'dev' ) { DB::connection()- ...
- bzoj1045
题解: 随便推一下公式 然后发现是中位数 代码: #include<bits/stdc++.h> using namespace std; ],n; long long sum; int ...
- java局部变量,成员变量在堆和栈中的存储
对于局部变量,如果是基本类型,会把值直接存储在栈:如果是引用类型,比如String s = new String("william");会把其对象存储在堆,而把这个对象的引用(指针 ...
- webView 的种种
1.关于UI 我们在设置webview的时候,有时候会发现在加载的过程中会出现一个黑色的条条,在加载完成的时候有得时候继续存在,有得时候消失不见. 这个黑边是由于webView.scrollview向 ...