kruskal重构树

kruskal重构树,顾名思义,是在kruskal的时候顺便搞出来的一棵重构树,具体地说是一个堆。

先说说这个东西是怎么搞出来的吧:默认事先把边按边权从小到大排序,在kruskal的时候,如果当前加入的边连接的两个点\(x\)和\(y\)不在同一个连通块中,就新建一个节点作为\(x\)和\(y\)所在树的根节点的父亲,令这个节点的权值为这条边的权值,还有一般kruskal也要做的把并查集合并;在同一个连通块中就不管。

从模板题看看重构树的性质:BZOJ3732 Network

仔细观察发现重构树上两点的lca的权值就是这两点之间路径的最大边权的最小值。其实如果是按边权从大到小排序的话,lca的权值就是最小边权的最大值,我们就是用这条性质来这道做题的。

树剖lca最好了。

#include <cstdio>
#include <cctype>
#include <algorithm>
#define R register
#define I inline
#define B 1000000
using namespace std;
const int N = 300007;
char buf[B], *p1, *p2;
I char gc() { return p1 == p2 && (p2 = (p1 = buf) + fread(buf, 1, B, stdin), p1 == p2) ? EOF : *p1++; }
I int rd() {
R int f = 0;
R char c = gc();
while (c < 48 || c > 57)
c = gc();
while (c > 47 && c < 58)
f = f * 10 + (c ^ 48), c = gc();
return f;
}
int f[N], val[N], fa[N], son[N][2], dep[N], top[N], cnt;
struct edge{int x, y, z;}e[N];
I int operator < (edge a, edge b) { return a.z < b.z; }
I int find(int x) {
R int r = x, y;
while (f[r] ^ r)
r = f[r];
while (x ^ r)
y = f[x], f[x] = r, x = y;
return r;
}
void dfs1(int x, int f) {
fa[x] = f, dep[x] = dep[f] + 1;
if (son[x][0])
dfs1(son[x][0], x), dfs1(son[x][1], x);
}
void dfs2(int x, int t) {
top[x] = t;
if (son[x][0])
dfs2(son[x][0], t), dfs2(son[x][1], son[x][1]);
}
I int lca(int x, int y) {
while (top[x] ^ top[y])
dep[top[x]] > dep[top[y]] ? x = fa[top[x]] : y = fa[top[y]];
return dep[x] < dep[y] ? x : y;
}
int main() {
R int n = rd(), m = rd(), k = rd(), i, x, y;
for (i = 1; i <= m; ++i)
e[i] = (edge){rd(), rd(), rd()};
for (i = 1; i <= n; ++i)
f[i] = i;
sort(e + 1, e + m + 1), cnt = n;
for (i = 1; i <= m; ++i) {
x = find(e[i].x), y = find(e[i].y);
if (x ^ y) {
++cnt, f[cnt] = f[x] = f[y] = cnt, val[cnt] = e[i].z;
son[cnt][0] = x, son[cnt][1] = y;
}
}
dfs1(cnt, 0), dfs2(cnt, cnt);
for (i = 1; i <= k; ++i)
x = rd(), y =rd(), printf("%d\n", val[lca(x, y)]);
return 0;
}

了解更多的性质可以做做这些题:

[NOI2018]归程 题解

[ONTAK2010]Peaks 题解

[IOI2018] werewolf 狼人 题解

kruskal重构树的更多相关文章

  1. [bzoj 3732] Network (Kruskal重构树)

    kruskal重构树 Description 给你N个点的无向图 (1 <= N <= 15,000),记为:1-N. 图中有M条边 (1 <= M <= 30,000) ,第 ...

  2. 【BZOJ 3732】 Network Kruskal重构树+倍增LCA

    Kruskal重构树裸题, Sunshine互测的A题就是Kruskal重构树,我通过互测了解到了这个神奇的东西... 理解起来应该没什么难度吧,但是我的Peaks连WA,,, 省选估计要滚粗了TwT ...

  3. 【BZOJ-3545&3551】Peaks&加强版 Kruskal重构树 + 主席树 + DFS序 + 倍增

    3545: [ONTAK2010]Peaks Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 1202  Solved: 321[Submit][Sta ...

  4. BZOJ 3551: [ONTAK2010]Peaks加强版 [Kruskal重构树 dfs序 主席树]

    3551: [ONTAK2010]Peaks加强版 题意:带权图,多组询问与一个点通过边权\(\le lim\)的边连通的点中点权k大值,强制在线 PoPoQQQ大爷题解传送门 说一下感受: 容易发现 ...

  5. bzoj 3551 kruskal重构树dfs序上的主席树

    强制在线 kruskal重构树,每两点间的最大边权即为其lca的点权. 倍增找,dfs序对应区间搞主席树 #include<cstdio> #include<cstring> ...

  6. kruskal重构树学习笔记

    \(kruskal\) 重构树学习笔记 前言 \(8102IONCC\) 中考到了,本蒟蒻不会,所以学一下. 前置知识 \(kruskal​\) 求最小(大)生成树,树上求 \(lca​\). 算法详 ...

  7. Kruskal重构树入门

    这个知识点好像咕咕咕了好长了..趁还没退役赶紧补一下吧.. 讲的非常简略,十分抱歉.. 前置知识 Kruskal算法 一定的数据结构基础(如主席树) Kruskal重构树 直接bb好像不是很好讲,那就 ...

  8. UOJ#407. 【IOI2018】狼人 Kruskal,kruskal重构树,主席树

    原文链接https://www.cnblogs.com/zhouzhendong/p/UOJ407.html 题解 套路啊. 先按照两个节点顺序各搞一个kruskal重构树,然后问题转化成两棵krus ...

  9. LOJ.2865.[IOI2018]狼人(Kruskal重构树 主席树)

    LOJ 洛谷 这题不就是Peaks(加强版)或者归程么..这算是\(IOI2018\)撞上\(NOI2018\)的题了? \(Kruskal\)重构树(具体是所有点按从小到大/从大到小的顺序,依次加入 ...

  10. 洛谷P4768 [NOI2018]归程(Kruskal重构树)

    题意 直接看题目吧,不好描述 Sol 考虑暴力做法 首先预处理出从$1$到每个节点的最短路, 对于每次询问,暴力的从这个点BFS,从能走到的点里面取$min$ 考虑如何优化,这里要用到Kruskal重 ...

随机推荐

  1. iOS设计模式 - 命令

    iOS设计模式 - 命令 原理图 说明 命令对象封装了如何对目标执行指令的信息,因此客户端或调用者不必了解目标的任何细节,却仍可以对他执行任何已有的操作.通过把请求封装成对象,客户端可以把它参数化并置 ...

  2. 获取图片的metaData

    获取图片的metaData 获取简易的metaData较为容易,以下是测试图: 以下是本人提供的源码: UIImage+MetaData.h // // UIImage+MetaData.h // P ...

  3. 【ORACLE】 安装需要注意的问题(一)

    安装ORACLE虽然不是很难,但是有时候很容易因为一些小细节导致安装失败,浪费大量的时间. 这里总结一下安装ORACLE的时候需要注意的问题,以及解决的办法 问题1:系统先决条件检查 正在检查操作系统 ...

  4. Mac OS X 10.9 Mavericks 无法启动 WebStorm(PhpStorm)

    手滑把Mac的系统升到了10.9,结果机子上的PhpStorm6.0启动不了. 十分天真的重装了一次PhpStorm,问题依然没有修复. 开始怨念苹果的这次升级,毕竟以往的升级都是无缝的,升级OS就应 ...

  5. Java Math类学习

    1.  java.lang.Math Math类其成员皆为静态成员(static),无需创建对象,直接用类名Math作为前缀使用它们即可. 2.  Math类有两个静态常量:E(自然对数)和PI(圆周 ...

  6. python第八课——random模块的使用

    2.2.如何获取随机整数值? 引入random模块的使用 randint(a,b)函数:作用:返回给程序一个[a,b]范围内的随机整数注意:含头含尾闭区间 思路步骤: 第一步:导入random模块到相 ...

  7. Jupyter Notebook的使用

    命令模式 (按键 Esc 开启) Enter : 转入编辑模式 Shift-Enter : 运行本单元,选中下个单元 Ctrl-Enter : 运行本单元 Alt-Enter : 运行本单元,在其下插 ...

  8. AOP:选择正确的时机进行编织

    在本文中,我们将采用三种重要的实现的例子,来实践本文提出的概念.这三种 AOP 实现是 AspectJ,Spring 和 JBoss.通过比较他们在 Weave 时机方面的不同,来获得对于如何选择 W ...

  9. P2110 欢总喊楼记

    题目描述 诗经有云: 关关雎鸠,在河之洲.窈窕淑女,君子好逑. 又是一个被风吹过的夏天--一日欢总在图书馆中自习,抬起头来,只见一翩跹女子从面前飘过,真是回眸一笑百媚生,六宫粉黛无颜色!一阵诗情涌上欢 ...

  10. 安卓预览报错 Failed to load AppCompat ActionBar with unknown error

    报错信息 : Render ProblemFailed to load AppCompat ActionBar with unknown error. Failed to instantiate on ...