假如有n個集合,要進行對集合的合併或者判斷兩個數是否在同乙個集合中就要用到並查集。
int
find
(x)
我們用p[x]==x來判斷當前節點是否為根節點。
如果當前節點不是根節點,就進行遞推,繼續呼叫find(x),直到找到根節點,之後會進行路徑壓縮,讓根節點的所有子節點都指向根節點。返回值是當前節點的根節點。
一共有n個數,編號是1~n,最開始每個數各自在乙個集合中。
現在要進行m個操作,操作共有兩種:
「m a b」,將編號為a和b的兩個數所在的集合合併,如果兩個數已經在同乙個集合中,則忽略這個操作;
「q a b」,詢問編號為a和b的兩個數是否在同乙個集合中;
第一行輸入整數n和m。
接下來m行,每行包含乙個操作指令,指令為「m a b」或「q a b」中的一種。
對於每個詢問指令」q a b」,都要輸出乙個結果,如果a和b在同一集合內,則輸出「yes」,否則輸出「no」。
每個結果佔一行。
1≤n,m≤105
4 5m 1 2
m 3 4
q 1 2
q 1 3
q 3 4
yesno
yes
#include
using
namespace std;
int p[
100010];
intfind
(int x)
intmain()
int x = m;
for(
int j =
1; j <= x;
++j)
else}}
return0;
}
原題鏈結 P1621 集合 並查集 素數
p1621 集合 並查集 素數 傳送門題目描述 caima 給你了所有 a,b 範圍內的整數。一開始每個整數都屬於各自的集合。每次你需要選擇兩個屬於不同集合的整數,如果這兩個整數擁有大於等於 p 的公共質因數,那麼把它們所在的集合合併。重複如上操作,直到沒有可以合併的集合為止。現在 caima 想知...
並查集(合併,查詢)
並查集用於管理元素分組情況的資料結構,判斷某一組合是否存在於同一集合 擁有同一性質 樹形結構實現但非二叉樹,但是通過rank比較可以優化為類似平衡二叉樹 int par 1000000 int rank 1000000 統計樹的深度 int size 1000000 統計每一棵樹結點個數 void ...
51NOD 1821 最優集合 並查集
傳送門 題意 乙個集合s的優美值定義為 最大的x,滿足對於任意i 1,x 都存在乙個s的子集s 使得s 中元素之和為i。給定n個集合,對於每一次詢問,指定乙個集合s1和乙個集合s2,以及乙個數k,要求選擇乙個s2的子集s3 s3 k 使得s1 s3的優美值最大。集合元素可以重複 n,m le 100...