bzoj 3674 可持久化並查集加強版

2022-06-01 02:27:09 字數 1734 閱讀 5157

題目大意:

1 a b 合併a,b所在集合

2 k 回到第k次操作之後的狀態(查詢算作操作)

3 a b 詢問a,b是否屬於同一集合,是則輸出1否則輸出0

思路:因為每次只會改乙個點的$fa$,可以使用主席樹暴力維護,$find$的時候不路徑壓縮 暴力跳

1 #include2 #include3 #include4 #include5 #include6 #include7 #include8 #include9 #include10 #include

11#define ll long long

12#define db double

13#define inf 2139062143

14#define maxn 200100

15#define rep(i,s,t) for(register int i=(s),i##__end=(t);i<=i##__end;++i)

16#define dwn(i,s,t) for(register int i=(s),i##__end=(t);i>=i##__end;--i)

17#define ren for(register int i=fst[x];i;i=nxt[i])

18#define pb(i,x) vec[i].push_back(x)

19#define pls(a,b) (a+b)%mod

20#define mns(a,b) (a-b+mod)%mod

21#define mul(a,b) (1ll*(a)*(b))%mod

22using

namespace

std;

23 inline int

read()

2427

while(isdigit(ch))

28return x*f;29}

30int n,m,rt[maxn],ls[maxn<<5],rs[maxn<<5],rk[maxn<<5],fa[maxn<<5

];31

inttot,las;

32void build(int &k,int l,int

r)33

int mid=l+r>>1

;35 build(ls[k],l,mid);build(rs[k],mid+1

,r);36}

37void mdf(int &k,int kk,int l,int r,int x,int

pa)38

int mid=l+r>>1;40

if(x<=mid) rs[k]=rs[kk],mdf(ls[k],ls[kk],l,mid,x,pa);

41else ls[k]=ls[kk],mdf(rs[k],rs[kk],mid+1

,r,x,pa);42}

43void add(int k,int l,int r,int

x)44

int mid=l+r>>1

;46 x<=mid?add(ls[k],l,mid,x):add(rs[k],mid+1

,r,x) ;47}

48int query(int k,int l,int r,int

x)49

53int find(int id,int x)

54void merge(int id,int x,int

y)55

60int

main()

6170 }

view code

BZOJ 3674 可持久化並查集

3674 可持久化並查集加強版 time limit 15 sec memory limit 256 mb submit 4051 solved 1503 submit status discuss description description 自從zkysb出了可持久化並查集後 hzwer 亂寫...

bzoj 3674 可持久化並查集)

傳送門 題解 一道可持久化並查集的裸題,板子子對了就能過 可持久化並查集是基於主席數的一種結構,可持久化並查集要求能夠訪問歷史版本,跟主席樹很像,所以可以通過主席樹維護普通並查集的fa陣列,但是由於用主席樹維護後沒有辦法用路徑壓縮,所以需要採用新的合併方式 啟發式合併,對每乙個節點增加乙個level...

bzoj 3674 可持久化並查集加強版

description 自從zkysb出了可持久化並查集後 hzwer 亂寫能ac,暴力踩標程 kuribohg 我不路徑壓縮就過了!ndsf 暴力就可以輕鬆虐!zky bzoj 3673的加強版。就沒了。include using namespace std const int n 200000 ...