Union By Rank and Path Compression in Union-Find Algorithm


The algorithm known as Union-Find (or Disjoint-Set) is in charge of maintaining distinct sets and offers operations to verify membership in a set and to combine sets together. It adeptly handles the union and find operations, both crucial for maintaining current connectivity information between elements.

Syntax

To ensure clarity let us first comprehend the syntax of the methods that are to be utilized in the upcoming code examples.

// Method to perform Union operation
void Union(int x, int y);

// Method to find the representative element of a set
int Find(int x);

Algorithm

The Union-Find algorithm consists of two fundamental operations − Union and Find. The Union operation merges two sets, and the Find operation determines the representative element of a set. By applying the Union and Find operations iteratively, we can build an efficient Union-Find data structure.

Union by Rank

The Union by Rank technique is used to optimize the Union operation by ensuring that the smaller tree is always attached to the root of the larger tree. This approach prevents the trees from becoming too imbalanced, which would lead to inefficient find operations.

The algorithm for Union by Rank is as follows −

  • Find the representatives (root elements) of the sets containing elements x and y.

  • If the representatives are the same, return.

  • If the rank of the representative of x is greater than the rank of the representative of y, make y's representative point to x's representative and update the rank of x's representative.

  • Otherwise, make x's representative point to y's representative and update the rank of y's representative if necessary.

Path Compression

Path Compression is another optimization technique that reduces the height of the trees in the Union-Find data structure. It aims to flatten the paths during the find operation, resulting in shorter paths for subsequent operations.

  • The algorithm for Path Compression is as follows −

  • Find the representative (root element) of the set containing element x.

  • While traversing the path from x to its representative, make each visited element directly point to the representative.

Approaches

Now that we have understood the basic concepts of Union by Rank and Path Compression, let's discuss two different approaches to implementing the Union-Find algorithm in C++.

Approach 1: Array-based Implementation

In this approach, we represent each set as an array. The value at each index represents the parent of the element. Initially, each element is its own parent, indicating that it is a representative of its set.

Algorithm

  • Let us begin the initialization process of the parent array. Each element will be assigned its own parent.

  • Implement the Find operation using path compression.

  • Implement the Union operation using Union by Rank.

Example

#include <iostream>
#define MAX_SIZE 100

// Initialize parent array
int parent[MAX_SIZE];
int rank[MAX_SIZE];

void makeSet(int n) {
   for (int i = 0; i < n; i++) {
      parent[i] = i;
      rank[i] = 0;
   }
}

int find(int x) {
   if (parent[x] != x) {
      parent[x] = find(parent[x]); // Path compression
   }
   return parent[x];
}

void Union(int x, int y) {
   int xRoot = find(x);
   int yRoot = find(y);
    
   if (xRoot == yRoot) {
      return;
   }
    
   // Union by rank
   if (rank[xRoot] < rank[yRoot]) {
      parent[xRoot] = yRoot;
   } else if (rank[xRoot] > rank[yRoot]) {
      parent[yRoot] = xRoot;
   } else {
      parent[yRoot] = xRoot;
      rank[xRoot]++;
   }
}

int main() {
   // Usage example
   makeSet(10); // Assuming 10 elements in the set
   Union(1, 2);
   Union(3, 4);
    
   // Print parent array
   for (int i = 0; i < 10; i++) {
      std::cout << "Element " << i << " Parent: " << parent[i] << std::endl;
   }
    
   return 0;
}

Output

Element 0 Parent: 0
Element 1 Parent: 1
Element 2 Parent: 1
Element 3 Parent: 3
Element 4 Parent: 3
Element 5 Parent: 5
Element 6 Parent: 6
Element 7 Parent: 7
Element 8 Parent: 8
Element 9 Parent: 9

Approach 2: Tree-based Implementation

To depict sets in our study, we utilize a methodology based on trees. Each item within the group associates with its respective parent node, whilst we designate the root node to represent that specific set.

Algorithm

  • Initialize the parent array, where each element is its own parent.

  • Implement the Find operation using path compression and recursive tree traversal.

  • Implement the Union operation using Union by Rank.

  • Full Executable Codes

Example

#include <iostream>

#define MAX_SIZE 100

// Initialize parent array
int parent[MAX_SIZE];
int rank[MAX_SIZE];

void makeSet(int n) {
   for (int i = 0; i < n; i++) {
      parent[i] = i;
      rank[i] = 0;
   }
}

int find(int x) {
   if (parent[x] != x) {
      parent[x] = find(parent[x]); // Path compression
   }
   return parent[x];
}

void Union(int x, int y) {
   int xRoot = find(x);
   int yRoot = find(y);
   
   if (xRoot == yRoot) {
      return;
   }
    
   // Union by rank
   if (rank[xRoot] < rank[yRoot]) {
      parent[xRoot] = yRoot;
   } else if (rank[xRoot] > rank[yRoot]) {
      parent[yRoot] = xRoot;
   } else {
      parent[yRoot] = xRoot;
      rank[xRoot]++;
   }
}

int main() {
   // Usage example
   makeSet(10); // Assuming 10 elements in the set
   Union(1, 2);
   Union(3, 4);
    
   // Print parent array
   for (int i = 0; i < 10; i++) {
      std::cout << "Element " << i << " Parent: " << parent[i] << std::endl;
   }
    
   return 0;
}

Output

Element 0 Parent: 0
Element 1 Parent: 1
Element 2 Parent: 1
Element 3 Parent: 3
Element 4 Parent: 3
Element 5 Parent: 5
Element 6 Parent: 6
Element 7 Parent: 7
Element 8 Parent: 8
Element 9 Parent: 9

Conclusion

In conclusion, Union by Rank and Path Compression are crucial techniques in the Union-Find algorithm. They optimize the Union and Find operations, respectively, leading to improved performance and efficient connectivity information management. By implementing these techniques in C++, we can effectively solve problems related to sets, connectivity, and graphs.

To summarize, we covered the syntax, step-by-step algorithms, and provided two real executable code examples in C++. By understanding and applying Union by Rank and Path Compression, you can enhance your algorithmic skills and tackle complex problems more effectively.

Updated on: 25-Jul-2023

1K+ Views

Kickstart Your Career

Get certified by completing the course

Get Started
Advertisements