Given an undirected graph G(V, E) consisting of2 N vertices and M edges, the task is to find the smallest vertex in the connected component of the vertex i for all values of i in the range [1, N].
Examples:
Input: N = 5, edges[] = {{1, 2}, {2, 3}, {4, 5}} Output: 1 1 1 4 4 Explanation: The given graph can be divided into a set of two connected components, i.e, {1, 2, 3} and {4, 5}.
- For i = 1, vertex 1 belongs to the component {1, 2, 3}. Therefore, the minimum vertex in the set is 1.
- For i = 2, vertex 2 belongs to the component {1, 2, 3}. Therefore, the minimum vertex in the set is 1.
- For i = 3, vertex 3 belongs to the component {1, 2, 3}. Therefore, the minimum vertex in the set is 1.
- For i = 4, vertex 4 belongs to the component {4, 5}. Therefore, the minimum vertex in the set is 4.
- For i = 5, vertex 5 belongs to the component {4, 5}. Therefore, the minimum vertex in the set is 4.
Input: N = 6, edges[] = {{1, 3}, {2, 4}} Output: 1 2 1 2 5 6
Approach: The given problem can be solved efficiently with the help of Disjoint Set Union. It can be observed that the vertices connected by an edge can be united into the same set and an unordered map can be used to keep track of the smallest vertex of each of the formed sets. Below are the steps to follow:
- Implement the find_set and union_set function of the Disjoint Set Union using the approach discussed in this article where find_set(x) returns the set number containing x, and union_set(x, y) unites the set containing x with the set containing y.
- Traverse the given array edges[] and for each edge (u, v), unite the set containing u with the set containing v.
- Create an unordered map minVal, where minVal[x] stores the minimum vertex of the set containing x as an element.
- Iterate over all vertices using a variable i and for each vertex set the value of minVal[find_set(node i)] to the minimum of minVal[find_set(i)] and i.
- After completing the above steps, for each vertex, i in the range [1, N], print the value of minVal[find_set(i)] as the result.
Below is the implementation of the above approach:
C++
#include <bits/stdc++.h>
using namespace std;
const int maxn = 100;
int parent[maxn], Size[maxn];
void make_set( int v)
{
parent[v] = v;
Size[v] = 1;
}
int find_set( int v)
{
if (v == parent[v]) {
return v;
}
return parent[v] = find_set(
parent[v]);
}
void union_sets( int a, int b)
{
a = find_set(a);
b = find_set(b);
if (a != b) {
if (Size[a] < Size[b])
swap(a, b);
parent[b] = a;
Size[a] += Size[b];
}
}
void findMinVertex(
int N, vector<pair< int , int > > edges)
{
for ( int i = 1; i <= N; i++) {
make_set(i);
}
for ( int i = 0; i < edges.size(); i++) {
union_sets(edges[i].first,
edges[i].second);
}
unordered_map< int , int > minVal;
for ( int i = 1; i <= N; i++) {
if (minVal[find_set(i)] == 0) {
minVal[find_set(i)] = i;
}
else {
minVal[find_set(i)]
= min(minVal[find_set(i)], i);
}
}
for ( int i = 1; i <= N; i++) {
cout << minVal[find_set(i)] << " " ;
}
}
int main()
{
int N = 6;
vector<pair< int , int > > edges
= { { 1, 3 }, { 2, 4 } };
findMinVertex(N, edges);
return 0;
}
|
Java
import java.util.*;
public class Main {
static int [] parent = new int [ 100 ];
static int [] Size = new int [ 100 ];
static void make_set( int v)
{
parent[v] = v;
Size[v] = 1 ;
}
static int find_set( int v)
{
if (v == parent[v]) {
return v;
}
return parent[v] = find_set(parent[v]);
}
static void union_sets( int a, int b)
{
a = find_set(a);
b = find_set(b);
if (a != b) {
if (Size[a] < Size[b]) {
int temp = a;
a = b;
b = temp;
}
parent[b] = a;
Size[a] += Size[b];
}
}
static void
findMinVertex( int N,
ArrayList<ArrayList<Integer> > edges)
{
for ( int i = 1 ; i <= N; i++) {
make_set(i);
}
for ( int i = 0 ; i < edges.size(); i++) {
union_sets(edges.get(i).get( 0 ),
edges.get(i).get( 1 ));
}
Map<Integer, Integer> minVal = new HashMap<>();
for ( int i = 1 ; i <= N; i++) {
if (!minVal.containsKey(find_set(i))) {
minVal.put(find_set(i), i);
}
else {
minVal.put(
find_set(i),
Math.min(( int )minVal.getOrDefault(
(Integer)find_set(i), 0 ),
i));
}
}
for ( int i = 1 ; i <= N; i++) {
System.out.print(minVal.get(find_set(i)) + " " );
}
}
public static void main(String[] args)
{
int N = 6 ;
ArrayList<ArrayList<Integer> > edges
= new ArrayList<ArrayList<Integer> >();
ArrayList<Integer> a1 = new ArrayList<Integer>();
a1.add( 1 );
a1.add( 3 );
edges.add(a1);
ArrayList<Integer> a2 = new ArrayList<Integer>();
a2.add( 2 );
a2.add( 4 );
edges.add(a2);
findMinVertex(N, edges);
}
}
|
Python3
maxn = 100
parent = [ 0 ] * maxn
Size = [ 0 ] * maxn
def make_set(v):
parent[v] = v
Size[v] = 1
def find_set(v):
if (v = = parent[v]):
return v
parent[v] = find_set(
parent[v])
return parent[v]
def union_sets(a, b):
a = find_set(a)
b = find_set(b)
if (a ! = b):
if (Size[a] < Size[b]):
a, b = b, a
parent[b] = a
Size[a] + = Size[b]
def findMinVertex(
N, edges):
for i in range ( 1 , N + 1 ):
make_set(i)
for i in range ( len (edges)):
union_sets(edges[i][ 0 ],
edges[i][ 1 ])
minVal = {}
for i in range ( 1 , N + 1 ):
if (find_set(i) not in minVal):
minVal[find_set(i)] = i
else :
minVal[find_set(i)] = min (minVal[find_set(i)], i)
for i in range ( 1 , N + 1 ):
print (minVal[find_set(i)], end = " " )
if __name__ = = "__main__" :
N = 6
edges = [[ 1 , 3 ], [ 2 , 4 ]]
findMinVertex(N, edges)
|
C#
using System;
using System.Collections.Generic;
using System.Linq;
class Program {
static int [] parent = new int [100];
static int [] Size = new int [100];
static void make_set( int v)
{
parent[v] = v;
Size[v] = 1;
}
static int find_set( int v)
{
if (v == parent[v]) {
return v;
}
return parent[v] = find_set(parent[v]);
}
static void union_sets( int a, int b)
{
a = find_set(a);
b = find_set(b);
if (a != b) {
if (Size[a] < Size[b]) {
int temp = a;
a = b;
b = temp;
}
parent[b] = a;
Size[a] += Size[b];
}
}
static void findMinVertex( int N, List<List< int > > edges)
{
for ( int i = 1; i <= N; i++) {
make_set(i);
}
for ( int i = 0; i < edges.Count(); i++) {
union_sets(edges[i][0], edges[i][1]);
}
Dictionary< int , int > minVal
= new Dictionary< int , int >();
for ( int i = 1; i <= N; i++) {
if (!minVal.ContainsKey(find_set(i))) {
minVal.Add(find_set(i), i);
}
else {
minVal[find_set(i)] = Math.Min(
( int )minVal.GetValueOrDefault(
( int )find_set(i), 0),
i);
}
}
for ( int i = 1; i <= N; i++) {
Console.Write( "{0} " , minVal.GetValueOrDefault(
( int )find_set(i), 0));
}
}
public static void Main()
{
int N = 6;
List<List< int > > edges = new List<List< int > >();
List< int > a1 = new List< int >();
a1.Add(1);
a1.Add(3);
edges.Add(a1);
List< int > a2 = new List< int >();
a2.Add(2);
a2.Add(4);
edges.Add(a2);
findMinVertex(N, edges);
}
}
|
Javascript
<script>
const maxn = 100;
let parent = new Array(maxn);
let Size = new Array(maxn);
function make_set(v)
{
parent[v] = v;
Size[v] = 1;
}
function find_set(v)
{
if (v == parent[v]) {
return v;
}
return parent[v] = find_set(parent[v]);
}
function union_sets(a, b)
{
a = find_set(a);
b = find_set(b);
if (a != b) {
if (Size[a] < Size[b]){
let temp = a;
a = b;
b = temp;
}
parent[b] = a;
Size[a] += Size[b];
}
}
function findMinVertex(N,edges)
{
for (let i = 1; i <= N; i++) {
make_set(i);
}
for (let i = 0; i < edges.length; i++) {
union_sets(edges[i][0],edges[i][1]);
}
let minVal = new Map();
for (let i = 1; i <= N; i++) {
if (minVal.has(find_set(i)) == false ) {
minVal.set(find_set(i),i);
}
else
{
minVal.set(find_set(i), Math.min(minVal.get(find_set(i)), i));
}
}
for (let i = 1; i <= N; i++) {
document.write(minVal.get(find_set(i)), " " );
}
}
let N = 6;
let edges = [ [ 1, 3 ], [ 2, 4 ] ];
findMinVertex(N, edges);
</script>
|
Time Complexity: O(N) Auxiliary Space: O(N)
|