File tree 6 files changed +205
-0
lines changed
Graphs/UnionFind/DisjointSet
6 files changed +205
-0
lines changed Original file line number Diff line number Diff line change
1
+ # The vey basics of union find and disjoint sets
2
+ # Basically an array and within that array lies a disjoint set
3
+
4
+
5
+ # There are two functions when discussing disjoint sets
6
+
7
+ # find(a) which takes in a single argument and returns the root of
8
+ # that particular node
9
+
10
+ # union(a,b) which takes in two arguments and combines them together
11
+ # let's watch a quick video on how this works and then implement from there
12
+
13
+ # First lets implement UnionFind as an object and instantiate it with an array
14
+
15
+ class UnionFind :
16
+ def __init__ (self , size ):
17
+ self .root = [i for i in range (size )]
18
+
19
+ # union connects two nodes with a left bias meaning that b will always
20
+ # connect to a
21
+ def union (self , x , y ):
22
+ rootX = self .find (x )
23
+ rootY = self .find (y )
24
+ if rootX != rootY :
25
+ for i in range (len (self .root )):
26
+ if self .root [i ] == rootY :
27
+ self .root [i ] = rootX
28
+
29
+ # takes in a node a and returns the root node of such
30
+ def find (self , a ):
31
+ while a != self .root [a ]:
32
+ a = self .root [a ]
33
+ return a
34
+
35
+ uu = UnionFind (10 )
36
+
37
+ print (uu .root )
38
+ uu .union (0 ,1 )
39
+ uu .union (0 ,2 )
40
+ uu .union (1 ,3 )
41
+ uu .union (4 ,8 )
42
+ uu .union (5 ,6 )
43
+ uu .union (5 ,7 )
44
+ print (uu .root )
45
+ print ([i for i in range (10 )])
Original file line number Diff line number Diff line change
1
+
2
+ class UnionFind :
3
+ def __init__ (self ,size ):
4
+ self .root = [i for i in range (size )]
5
+
6
+ def find (self , n ):
7
+ if self .root [n ] == n :
8
+ return n
9
+
10
+ self .root [n ] = self .find (self .root [n ])
11
+ return self .root [n ]
12
+ # quick union
13
+ def union (self , a , b ):
14
+ fa = self .find (a )
15
+ fb = self .find (b )
16
+ if fa != fb :
17
+ self .root [fa ] = fb
18
+
19
+ def connected (self , x , y ):
20
+ return self .find (x ) == self .find (y )
21
+ # Test Case
22
+ uf = UnionFind (10 )
23
+ # 1-2-5-6-7 3-8-9 4
24
+ uf .union (1 , 2 )
25
+ uf .union (2 , 5 )
26
+ uf .union (5 , 6 )
27
+ uf .union (6 , 7 )
28
+ uf .union (3 , 8 )
29
+ uf .union (8 , 9 )
30
+ print (uf .connected (1 , 5 )) # true
31
+ print (uf .connected (5 , 7 )) # true
32
+ print (uf .connected (4 , 9 )) # false
33
+ # 1-2-5-6-7 3-8-9-4
34
+ uf .union (9 , 4 )
35
+ print (uf .connected (4 , 9 )) # true
Original file line number Diff line number Diff line change
1
+ class UnionFind :
2
+ def __init__ (self , size ):
3
+ self .root = [i for i in range (size )]
4
+ # changing quickfind to have the parent node be stored in the array
5
+ # effectively making it an O(1) operation to find the root of a given node
6
+ # however, union will take a hit in performance
7
+
8
+ def find (self , n ):
9
+ return self .root [n ]
10
+
11
+ def union (self , a , b ):
12
+ fa = self .find (a )
13
+ fb = self .find (b )
14
+ if fa != fb :
15
+ for i , v in enumerate (self .root ):
16
+ if fa == v :
17
+ self .root [i ] = fb
18
+
19
+ def connected (self , x , y ):
20
+ return self .find (x ) == self .find (y )
21
+
22
+
23
+ # Test Case
24
+ uf = UnionFind (10 )
25
+ # 1-2-5-6-7 3-8-9 4
26
+ uf .union (1 , 2 )
27
+ uf .union (2 , 5 )
28
+ uf .union (5 , 6 )
29
+ uf .union (6 , 7 )
30
+ uf .union (3 , 8 )
31
+ uf .union (8 , 9 )
32
+ print (uf .connected (1 , 5 )) # true
33
+ print (uf .connected (5 , 7 )) # true
34
+ print (uf .connected (4 , 9 )) # false
35
+ # 1-2-5-6-7 3-8-9-4
36
+ uf .union (9 , 4 )
37
+ print (uf .connected (4 , 9 )) # true
Original file line number Diff line number Diff line change
1
+ # The vey basics of union find and disjoint sets
2
+ # Basically an array and within that array lies a disjoint set
3
+
4
+
5
+ # There are two functions when discussing disjoint sets
6
+
7
+ # find(a) which takes in a single argument and returns the root of
8
+ # that particular node
9
+
10
+ # union(a,b) which takes in two arguments and combines them together
11
+ # let's watch a quick video on how this works and then implement from there
12
+
13
+ # First lets implement UnionFind as an object and instantiate it with an array
14
+
15
+ class UnionFind :
16
+ def __init__ (self , size ):
17
+ self .root = [i for i in range (size )]
18
+
19
+ # union connects two nodes with a left bias meaning that b will always
20
+ # connect to a
21
+ def union (self ,a ,b ):
22
+ # Basically we want to take the parent node of the given thing
23
+ fa = self .find (a )
24
+ fb = self .find (b )
25
+ if fa != fb :
26
+ self .root [fa ] = fb
27
+
28
+ # takes in a node a and returns the root node of such
29
+ def find (self , a ):
30
+ while a != self .root [a ]:
31
+ a = self .root [a ]
32
+ return a
33
+
34
+ uu = UnionFind (10 )
35
+
36
+ print (uu .root )
37
+ uu .union (0 ,1 )
38
+ uu .union (0 ,2 )
39
+ uu .union (1 ,3 )
40
+ uu .union (4 ,8 )
41
+ uu .union (5 ,6 )
42
+ uu .union (5 ,7 )
43
+ print (uu .root )
44
+ print ([i for i in range (10 )])
Original file line number Diff line number Diff line change
1
+ # Optimized union find program that implements union by rank
2
+
3
+ class UnionFind :
4
+ def __init__ (self , size ):
5
+ self .root = [i for i in range (size )]
6
+ self .rank = [1 ] * size
7
+
8
+ # Recurrsively update root
9
+ def find (self , n ):
10
+ if self .root [n ] != n :
11
+ self .root [n ] = self .find (self .root [n ])
12
+ return self .root [n ]
13
+
14
+ def union (self , a , b ):
15
+ fa = self .find (a )
16
+ fb = self .find (b )
17
+
18
+ if fa != fb :
19
+ if self .rank [fa ] > self .rank [fb ]:
20
+ self .root [fb ] = fa
21
+ elif self .rank [fa ] < self .rank [fb ]:
22
+ self .root [fa ] = fb
23
+ else :
24
+ self .root [fa ] = fb
25
+ self .rank [fb ] += 1
26
+
27
+ def connected (self , x , y ):
28
+ return self .find (x ) == self .find (y )
29
+
30
+ # Test Case
31
+ uf = UnionFind (10 )
32
+ # 1-2-5-6-7 3-8-9 4
33
+ uf .union (1 , 2 )
34
+ uf .union (2 , 5 )
35
+ uf .union (5 , 6 )
36
+ uf .union (6 , 7 )
37
+ uf .union (3 , 8 )
38
+ uf .union (8 , 9 )
39
+ print (uf .connected (1 , 5 )) # true
40
+ print (uf .connected (5 , 7 )) # true
41
+ print (uf .connected (4 , 9 )) # false
42
+ # 1-2-5-6-7 3-8-9-4
43
+ uf .union (9 , 4 )
44
+ print (uf .connected (4 , 9 )) # true
You can’t perform that action at this time.
0 commit comments