zoukankan      html  css  js  c++  java
  • 可持久化并查集

    如果不采用路径压缩而只采用按秩合并,那么并查集的可持久化是比较容易实现的。按秩合并可以保证一棵 $n$ 个节点的树的高度是 $O(log n)$ 的。

    实现方法:
    用 $r_v$ 表示 $v$ 所在子树的根。
    假设要将点 $u$ 和点 $v$ 所在子树和并(也就是将边 $(u,v)$ 加入图中),那么需要在合并之前记录一下 $r_u, mathrm{rank}(r_u)$ 和 $r_v, mathrm{rank}(r_v)$。
    要恢复到某个历史版本,就按与加边相反的顺序删边。

    const int N = 5e5 + 5;
    int par[N];
    int rk[N];
    
    int root(int x){
    	while(x != par[x]) x = par[x];
    	return x;
    }
    
    struct his{
    	int u, rk1;
    	int v, rk2;
    };
    
    his unite(int x, int y){
    	x = root(x);
    	y = root(y);
    
    	his res = {x, rk[x], y, rk[y]};
    
    	if(x == y) return res;
    	if(rk[x] > rk[y])
    		par[y] = x;
    	else{
    		par[x] = y;
    		if(rk[x] == rk[y])
    			++rk[y];
    	}
    	return res;
    }
    
    
    void divide(const his &x){
    	par[x.u] = x.u;
    	par[x.v] = x.v;
    	rk[x.u] = x.rk1;
    	rk[x.v] = x.rk2;
    }
    
  • 相关阅读:
    文档01_基础
    文档07_JavaScript_ajax
    文档02_JavaScript
    文档06_JavaScript_面相对象
    文档05_JavaScript_节点
    文档06_Asp.net2.0_01
    文档04_JavaScript_事件
    文档05_多线程
    文档03_JavaScript_函数
    根据日期计算星座
  • 原文地址:https://www.cnblogs.com/Patt/p/7856030.html
Copyright © 2011-2022 走看看