-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathListUnionFind.java
139 lines (131 loc) · 4.23 KB
/
ListUnionFind.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
import java.util.ArrayList;
public class ListUnionFind{
public class Node{
public Header head;
public int x;
public Node next;
public Node(Header h, int x1, Node n){
this.head = h;
this.x = x1;
this.next = n;
}
public String toString(){
if(next == null){
return "{ head : " + Integer.toString(head.first.x) + ", x : " + Integer.toString(x) + ", next : null }";
}
return "{ head : " + Integer.toString(head.first.x) + ", x : " + Integer.toString(x) + ", next : " + Integer.toString(next.x) + " }";
}
}
public class Header{
public Node first;
public int weight;
public Node tail;
public Header(Node f, int w, Node t){
this.first = f;
this.weight = w;
this.tail = t;
}
public String toString(){
return "{ first : " + Integer.toString(first.x) + ", weight : " + Integer.toString(weight) + ", tail : " + Integer.toString(tail.x) + " }";
}
}
public int size;
public Node[] element;
public ListUnionFind(int n){
makeSet(n);
}
/**
* This method will initialize the Union Find data structure and create the n singleton
* sets {0}, {1}, ..., {n-1}. This method must be called before any find()
* or union() method is called.
* NOTE: We could have this done by the constructor, UnionFind(n).
*
* @param n the size of the Universal Set
*/
public void makeSet(int n){
this.element = new Node[n];
for(int i = 0; i < n; i++){
Header h = new Header(null,1,null);
Node temp = new Node(h,i,null);
h.first = temp;
h.tail = temp;
element[i] = temp;
}
}
/**
* If x is in set S1 and y is in set S2, this method will create S1 U S2.
* NOTE: If S1=S2, there is no change to the data structure.
* @param x an element in the Universal Set U.
* @param y an element in the Universal Set U.
*/
public void union(int x, int y){
Header h;
Node temp;
if((find(x)==find(y))){
return;
}
if(element[x].head.weight > element[y].head.weight){
h = element[x].head;
temp = h.first;
h.tail.next = element[y].head.first;
while(temp != null){
temp.head = h;
temp = temp.next;
}
}
else if(element[y].head.weight > element[x].head.weight){
h = element[y].head;
temp = h.first;
h.tail.next = element[x].head.first;
while(temp != null){
temp.head = h;
temp = temp.next;
}
}
else{
h = element[y].head;
temp = h.first;
h.tail.next = element[x].head.first;
while(temp != null){
temp.head = h;
temp = temp.next;
}
h.weight++;
}
}
/**
* The find(x) method returns the set representative for x.
* @param x an element in the Universal Set U.
* @return the set representative for the set x is in.
*/
public int find(int x){
return element[x].head.first.x;
}
public String toString(){
String output = "";
ArrayList<Header> comp = new ArrayList<Header>();
for(int i = 0; i < element.length; i++){
if(!comp.contains(element[i].head)){
Node temp = element[i].head.first;
output = output + "{ ";
while(temp != null){
output = output + temp.toString();
temp = temp.next;
output = output + ", ";
}
output = output.substring(0, output.length()-2);
output = output + " }";
output = output + "\n";
comp.add(element[i].head);
}
}
return output;
}
public static void main(String[] args){
ListUnionFind l = new ListUnionFind(4);
System.out.println(l.toString());
l.union(0, 1);
System.out.println(l.toString());
System.out.println(l.find(0));
}
}