codeforces EDU Disjoint Sets Union step 1

本文以codeforces EDU Disjoint Sets Union为资料

introduction

Disjoint Sets Union

DSU是一种支持对 n n n个元素进行 g e t \bm{get} get u n i o n \bm{union} union的数据结构,
g e t ( a ) \bm{get(a)} get(a)表示获取 a \bm{a} a所属的集合。
u n i o n ( a ,   b ) \bm{union(a,\ b)} union(a, b)表示合并 a ,   b \bm{a,\ b} a, b所属的集合。

DSU使用 p [ i ] \bm{p[i]} p[i]表示 i \bm{i} i所属的集合,那么 u n i o n ( a ,   b ) \bm{union(a,\ b)} union(a, b)可以用 a \bm{a} a指向的头结点指向 b \bm{b} b指向的头结点,通过使用链的方式合并。一个有效降低时间复杂度的方法是对半,令 r [ i ] \bm{r[i]} r[i]表示 i \bm{i} i的阶,那么用低阶指向高阶可以使时间复杂度降为 O ( n l o g n ) O(nlogn) O(nlogn)
符合结合性和交换性的运算可以在 u n i o n \bm{union} union时计算,例如 s u m   o r   m i n \bm{sum}\ or\ \bm{min} sum or min

problems & solutions

C. Experience

u n i o n ( a ,   b ) \bm{union(a,\ b)} union(a, b)时,在低阶的extra上减去一个高阶的sum,这样,在从叶子结点到根节点的过程中,不属于当前节点的exp能被extra消去。

D. Cutting a graph

逆向,从后往前加边考虑。

E. Monkeys

逆向。一个解决1为根的方法是增加 m i n \bm{min} min函数。当 u n i o n ( a ,   b ) \bm{union(a,\ b)} union(a, b)其中有一个集合含1时,更新另一个节点的 t i m e time time,表示在当前时刻两个集合脱离(从前往后看)。考虑到一个集合对应的根节点指向另一个根节点时,最多会更新一次,那么这个方法是可行的。最后扫描所有点,访问其最近 t i m e time time存在的根节点,其 t i m e time time即为该根下所有点(不包含子根)脱离的时刻。一个方法是采取类似 g e t \bm{get} get的更新过程。

code

code on github

  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值