Open In App

# Maximum product of a pair of nodes from largest connected component in a Graph

Given an undirected weighted graph G consisting of N vertices and M edges, and two arrays Edges[][2] and Weight[] consisting of M edges of the graph and weights of each edge respectively, the task is to find the maximum product of any two vertices of the largest connected component of the graph, formed by connecting all edges with the same weight.

Examples:

Input: N = 4, Edges[][] = {{1, 2}, {1, 2}, {2, 3}, {2, 3}, {2, 4}}, Weight[] = {1, 2, 1, 3, 3}
Output: 12
Explanation:

• Components of edges of weight 1, 1 ? 2 ? 3. The maximum product of any two vertices of this component is 6.
• Components of edges of weight 2, 1 ? 2. The maximum product of any two vertices of this component is 2.
• Components of edges of weight 3, 4 ? 2 ? 3. The maximum product of any two vertices of this component is 12.

Therefore, the maximum product among all the connected components of size 3 (which is maximum) is 12.

Input: N = 5, Edges[][] = {{1, 5}, {2, 5}, {3, 5}, {4, 5}, {1, 2}, {2, 3}, {3, 4}}, Weight[] = {1, 1, 1, 1, 2, 2, 2}
Output: 20

Approach: The given problem can be solved by performing the DFS traversal on the given graph and maximize the product of the first and second maximum node for all the connected components of the same weight. Follow the steps below to solve the problem:

• Store all the edges corresponding to all the unique weight in a map M.
• Initialize a variable, say res as 0 to store the maximum product of any two nodes of the connected components of the same weights.
• Traverse the map and for each key as weight create a graph by connecting all the edges mapped with the particular weight and perform the following operations:
• Find the value of the maximum(say M1) and the second maximum(say M2) node’s value and the size of all the connected components of the graph by performing the DFS Traversal on the created graph.
• Update the value of res to the maximum of res, M1, and M2 if the size of the currently connected components is at least the largest size connected component found previously.
• After completing the above steps, print the value of res as the maximum product.

Below is the implementation of the above approach:

## C++

 `// C++ program for the above approach` `#include ``using` `namespace` `std;` `// Stores the first and second largest``// element in a connected component``int` `Max, sMax;` `// Stores the count of nodes``// in the connected components``int` `cnt = 0;` `// Function to perform DFS Traversal``// on a given graph and find the first``// and the second largest elements``void` `dfs(``int` `u, ``int` `N, vector<``bool``>& vis,``         ``vector >& adj)``{``    ``// Update the maximum value``    ``if` `(u > Max) {``        ``sMax = Max;``        ``Max = u;``    ``}` `    ``// Update the second max value``    ``else` `if` `(u > sMax) {``        ``sMax = u;``    ``}` `    ``// Increment size of component``    ``cnt++;` `    ``// Mark current node visited``    ``vis[u] = ``true``;` `    ``// Traverse the adjacent nodes``    ``for` `(``auto` `to : adj[u]) {` `        ``// If to is not already visited``        ``if` `(!vis[to]) {``            ``dfs(to, N, vis, adj);``        ``}``    ``}` `    ``return``;``}` `// Function to find the maximum``// product of a connected component``int` `MaximumProduct(``    ``int` `N, vector > Edge,``    ``vector<``int``> wt)``{``    ``// Stores the count of edges``    ``int` `M = wt.size();` `    ``// Stores all the edges mapped``    ``// with a particular weight``    ``unordered_map<``int``,``                  ``vector > >``        ``mp;` `    ``// Update the map mp``    ``for` `(``int` `i = 0; i < M; i++)``        ``mp[wt[i]].push_back(Edge[i]);` `    ``// Stores the result``    ``int` `res = 0;` `    ``// Traverse the map mp``    ``for` `(``auto` `i : mp) {` `        ``// Stores the adjacency list``        ``vector > adj(N + 1);` `        ``// Stores the edges of``        ``// a particular weight``        ``vector > v = i.second;` `        ``// Traverse the vector v``        ``for` `(``int` `j = 0; j < v.size(); j++) {` `            ``int` `U = v[j].first;``            ``int` `V = v[j].second;` `            ``// Add an edge``            ``adj[U].push_back(V);``            ``adj[V].push_back(U);``        ``}` `        ``// Stores if a vertex``        ``// is visited or not``        ``vector<``bool``> vis(N + 1, 0);` `        ``// Stores the maximum``        ``// size of a component``        ``int` `cntMax = 0;` `        ``// Iterate over the range [1, N]``        ``for` `(``int` `u = 1; u <= N; u++) {` `            ``// Assign Max, sMax, count = 0``            ``Max = sMax = cnt = 0;` `            ``// If vertex u is not visited``            ``if` `(!vis[u]) {` `                ``dfs(u, N, vis, adj);` `                ``// If cnt is greater``                ``// than cntMax``                ``if` `(cnt > cntMax) {` `                    ``// Update the res``                    ``res = Max * sMax;``                    ``cntMax = cnt;``                ``}` `                ``// If already largest``                ``// connected component``                ``else` `if` `(cnt == cntMax) {` `                    ``// Update res``                    ``res = max(res, Max * sMax);``                ``}``            ``}``        ``}``    ``}` `    ``// Return res``    ``return` `res;``}` `// Driver Code``int` `main()``{``    ``int` `N = 5;``    ``vector > Edges``        ``= { { 1, 2 }, { 2, 5 }, { 3, 5 }, { 4, 5 }, { 1, 2 }, { 2, 3 }, { 3, 4 } };` `    ``vector<``int``> Weight = { 1, 1, 1, 1,``                           ``2, 2, 2 };``    ``cout << MaximumProduct(N, Edges, Weight);` `    ``return` `0;``}`

## Java

 `// Java code to implement the approach``import` `java.util.*;``class` `GFG {` `  ``// Stores the first and second largest``  ``// element in a connected component``  ``static` `int` `Max, sMax, cnt;`  `  ``// Function to perform DFS Traversal``  ``// on a given graph and find the first``  ``// and the second largest elements``  ``static` `void` `dfs(``int` `u, ``int` `N, List vis,``                  ``List > adj) {` `    ``// Update the maximum value``    ``if` `(u > Max) {``      ``sMax = Max;``      ``Max = u;``    ``}` `    ``// Update the second max value``    ``else` `if` `(u > sMax) {``      ``sMax = u;``    ``}` `    ``// Increment size of component``    ``cnt++;` `    ``// Mark current node visited``    ``vis.set(u, ``true``);` `    ``// Traverse the adjacent nodes``    ``for` `(``int` `i = ``0``; i < adj.get(u).size(); i++) {``      ``int` `to = adj.get(u).get(i);` `      ``// If to is not already visited``      ``if` `(!vis.get(to)) {``        ``dfs(to, N, vis, adj);``      ``}``    ``}``  ``}` `  ``// Function to find the maximum``  ``// product of a connected component``  ``static` `int` `MaximumProduct(``int` `N, List<``int``[]> Edge, List wt) {``    ``int` `M = wt.size();` `    ``// Stores all the edges mapped``    ``// with a particular weight``    ``Map > mp = ``new` `HashMap<>();``    ``for` `(``int` `i = ``0``; i < M; i++) {``      ``if` `(!mp.containsKey(wt.get(i))) {``        ``mp.put(wt.get(i), ``new` `ArrayList<>());``      ``}``      ``mp.get(wt.get(i)).add(Edge.get(i));``    ``}``    ``List keys = ``new` `ArrayList<>(mp.keySet());``    ``Collections.sort(keys, Collections.reverseOrder());` `    ``// Stores the result``    ``int` `res = ``0``;` `    ``// Traverse the map mp``    ``for` `(Integer i : keys) {``      ``List > adj = ``new` `ArrayList<>();``      ``for` `(``int` `j = ``0``; j <= N; j++)``        ``adj.add(``new` `ArrayList<>());` `      ``// Stores the edges of``      ``// a particular weight``      ``List<``int``[]> v = mp.get(i);` `      ``// Traverse the vector v``      ``for` `(``int` `j = ``0``; j < v.size(); j++) {``        ``int` `U = v.get(j)[``0``];``        ``int` `V = v.get(j)[``1``];``        ``adj.get(U).add(V);``        ``adj.get(V).add(U);``      ``}` `      ``// Stores the maximum``      ``// size of a component``      ``List vis = ``new` `ArrayList<>();``      ``for` `(``int` `j = ``0``; j <= N; j++)``        ``vis.add(``false``);``      ``int` `cntMax = ``0``;``      ``for` `(``int` `u = ``1``; u <= N; u++) {` `        ``// Assign Max, sMax, count = 0``        ``Max = ``0``;``        ``sMax = ``0``;``        ``cnt = ``0``;` `        ``// If vertex u is not visited``        ``if` `(!vis.get(u)) {``          ``dfs(u, N, vis, adj);` `          ``// If cnt is greater``          ``// than cntMax``          ``if` `(cnt > cntMax) {` `            ``// Update the res``            ``res = Max * sMax;``            ``cntMax = cnt;``          ``}` `          ``// If already largest``          ``// connected component``          ``else` `if` `(cnt == cntMax) {` `            ``// Update res``            ``res = Math.max(res, Max * sMax);``          ``}``        ``}``      ``}``    ``}``    ``return` `res;``  ``}`  `  ``// Driver code``  ``public` `static` `void` `main(String[] args) {``    ``int` `N = ``5``;``    ``List<``int``[]> Edges = ``new` `ArrayList<>();``    ``Edges.add(``new` `int``[]{``1``, ``2``});``    ``Edges.add(``new` `int``[]{``2``, ``5``});``    ``Edges.add(``new` `int``[]{``3``, ``5``});``    ``Edges.add(``new` `int``[]{``4``, ``5``});``    ``Edges.add(``new` `int``[]{``1``, ``2``});``    ``Edges.add(``new` `int``[]{``2``, ``3``});``    ``Edges.add(``new` `int``[]{``3``, ``4``});` `    ``List Weights = Arrays.asList(``1``, ``1``, ``1``, ``1``, ``2``, ``2``, ``2``);` `    ``System.out.println(MaximumProduct(N, Edges, Weights));``  ``}``}` `// This code is contributed by phasing17`

## Python3

 `# Function to perform DFS Traversal``# on a given graph and find the first``# and the second largest elements``def` `dfs(u, N, vis, adj):``    ` `    ``global` `Max``    ``global` `sMax``    ``global` `cnt``    ` `    ``# Update the maximum value``    ``if` `u > ``Max``:``        ``sMax ``=` `Max``        ``Max` `=` `u``    ``# Update the second max value``    ``elif` `u > sMax:``        ``sMax ``=` `u``    ``# Increment size of component``    ``cnt``+``=``1` `    ``# Mark current node visited``    ``vis[u] ``=` `True``    ` `    ``# Traverse the adjacent nodes``    ``for` `to ``in` `adj[u]:``        ``# If to is not already visited``        ``if` `not` `vis[to]:``            ``dfs(to, N, vis, adj)` `def` `maximumProduct(N, Edge, wt):``    ``# Stores the count of edges``    ``M ``=` `len``(wt)` `    ``# Stores all the edges mapped``    ``# with a particular weight``    ``mp ``=` `{}` `    ``# Update the map mp``    ``for` `i ``in` `range``(M):``        ``weight ``=` `wt[i]``        ``if` `weight ``not` `in` `mp:``            ``mp[weight] ``=` `[Edge[i]]``        ``else``:``            ``mp[weight].append(Edge[i])` `    ``# Stores the result``    ``res ``=` `0``    ` `    ``keys ``=` `list``(mp.keys())``    ``keys.sort(reverse``=``True``)``    ``# Traverse the map mp``    ``for` `key ``in` `keys:``        ``weight ``=` `mp[key]``        ``# Stores the adjacency list``        ``adj ``=` `[ [] ``for` `_ ``in` `range``(N ``+` `1``)]` `        ``# Stores the edges of``        ``# a particular weight``        ``v ``=` `weight` `        ``# Traverse the vector v``        ``for` `j ``in` `range``(``len``(v)):``            ``U, V ``=` `v[j]` `            ``# Add an edge``            ``adj[U].append(V)``            ``adj[V].append(U)` `        ``# Stores if a vertex``        ``# is visited or not``        ``vis ``=` `[``False` `for` `_ ``in` `range``(N ``+` `1``)]` `        ``# Stores the maximum``        ``# size of a component``        ``cntMax ``=` `0` `        ``# Iterate over the range [1, N]``        ``for` `u ``in` `range``(``1``, N``+``1``):``            ` `            ``global` `Max``            ``global` `sMax``            ``global` `cnt` `            ``# Assign Max, sMax, count = 0``            ``Max` `=` `0``            ``sMax ``=` `0``            ``cnt ``=` `0``;` `            ``# If vertex u is not visited``            ``if` `not` `vis[u]:``                ``dfs(u, N, vis, adj);` `                ``# If cnt is greater``                ``# than cntMax``                ``if` `cnt > cntMax:``                    ``# Update the res``                    ``res ``=` `Max` `*` `sMax;``                    ``cntMax ``=` `cnt;``                `  `                ``# If already largest``                ``# connected component``                ``elif` `cnt ``=``=` `cntMax:` `                    ``# Update res``                    ``res ``=` `max``(res, ``Max` `*` `sMax);``    ``return` `res` `# driver code``N ``=` `5``;``Edges ``=` `[[``1``, ``2``], [``2``, ``5``], [``3``, ``5``], [``4``, ``5``], [``1``, ``2``], [``2``, ``3``], [``3``, ``4``]];``Weight ``=` `[``1``, ``1``, ``1``, ``1``, ``2``, ``2``, ``2``];``print``(maximumProduct(N, Edges, Weight));` `# This code is contributed by phasing17.`

## Javascript

 `// JavaScript implementation of the approach` `function` `dfs(u, N, vis, adj) {``    ``// Update the maximum value``    ``if` `(u > Max) {``        ``sMax = Max;``        ``Max = u;``    ``}` `    ``// Update the second max value``    ``else` `if` `(u > sMax) {``        ``sMax = u;``    ``}` `    ``// Increment size of component``    ``cnt++;` `    ``// Mark current node visited``    ``vis[u] = ``true``;``    ` `    ``// Traverse the adjacent nodes``    ``for` `(const to of adj[u]) {``        ``// If to is not already visited``        ``if` `(!vis[to]) {``            ``dfs(to, N, vis, adj);``        ``}``    ``}``}` `function` `maximumProduct(N, Edge, wt) {``    ` `    ``// Stores the count of edges``    ``const M = wt.length;` `    ``// Stores all the edges mapped``    ``// with a particular weight``    ``const mp = {};` `    ``// Update the map mp``    ``for` `(let i = 0; i < M; i++) {``        ``const weight = wt[i];``        ``if` `(!mp.hasOwnProperty(weight)) {``            ``mp[weight] = [Edge[i]];``        ``} ``else` `{``            ``mp[weight].push(Edge[i]);``        ``}``    ``}` `    ``// Stores the result``    ``let res = 0;``    ` `    ``let keys = Object.keys(mp)``    ``keys.sort(``function``(a, b)``    ``{``        ``return` `-a + b;``    ``})``    ``// Traverse the map mp``    ``for` `(const key of keys) {``        ``let weight = mp[key]``        ``// Stores the adjacency list``        ``const adj = ``new` `Array(N + 1);``        ``for` `(``var` `i = 0; i <= N; i++)``            ``adj[i] = []` `        ``// Stores the edges of``        ``// a particular weight``        ``const v = weight;` `        ``// Traverse the vector v``        ``for` `(let j = 0; j < v.length; j++) {` `            ``const U = v[j][0];``            ``const V = v[j][1];` `            ``// Add an edge``            ``let l1 = adj[U]``            ``l1.push(V)``            ``adj[U] = l1``            ` `            ``let l2 = adj[V]``            ``l2.push(U)``            ``adj[V] = l2``        ``}` `        ``// Stores if a vertex``        ``// is visited or not``        ``const vis = ``new` `Array(N + 1).fill(``false``)` `        ``// Stores the maximum``        ``// size of a component``        ``let cntMax = 0;` `        ``// Iterate over the range [1, N]``        ``for` `(let u = 1; u <= N; u++) {` `            ``// Assign Max, sMax, count = 0``            ``Max = 0``            ``sMax = 0``            ``cnt = 0;` `            ``// If vertex u is not visited``            ``if` `(!vis[u]) {``                ``dfs(u, N, vis, adj);` `                ``// If cnt is greater``                ``// than cntMax``                ``if` `(cnt > cntMax) {``                    ``// Update the res``                    ``res = Max * sMax;``                    ``cntMax = cnt;``                ``}` `                ``// If already largest``                ``// connected component``                ``else` `if` `(cnt == cntMax) {` `                    ``// Update res``                    ``res = Math.max(res, Max * sMax);``                ``}``            ``}``        ``}``    ``}``    ``return` `res``}` `// driver code``const N = 5;``const Edges = [[1, 2], [2, 5], [3, 5], [4, 5], [1, 2], [2, 3], [3, 4]];``const Weight = [1, 1, 1, 1, 2, 2, 2];``console.log(maximumProduct(N, Edges, Weight));`

## C#

 `// C# code to implement the approach` `using` `System;``using` `System.Collections.Generic;``using` `System.Linq;` `class` `MainClass {``    ``// Stores the first and second largest``    ``// element in a connected component``    ``static` `int` `Max, sMax;` `    ``// Stores the count of nodes``    ``// in the connected components``    ``static` `int` `cnt = 0;` `    ``// Function to perform DFS Traversal``    ``// on a given graph and find the first``    ``// and the second largest elements``    ``static` `void` `dfs(``int` `u, ``int` `N, List<``bool``> vis,``                    ``List > adj)``    ``{``        ``// Update the maximum value``        ``if` `(u > Max) {``            ``sMax = Max;``            ``Max = u;``        ``}` `        ``// Update the second max value``        ``else` `if` `(u > sMax) {``            ``sMax = u;``        ``}` `        ``// Increment size of component``        ``cnt++;` `        ``// Mark current node visited``        ``vis[u] = ``true``;` `        ``// Traverse the adjacent nodes``        ``for` `(``int` `i = 0; i < adj[u].Count; i++) {``            ``int` `to = adj[u][i];` `            ``// If to is not already visited``            ``if` `(!vis[to]) {``                ``dfs(to, N, vis, adj);``            ``}``        ``}` `        ``return``;``    ``}` `    ``// Function to find the maximum``    ``// product of a connected component``    ``static` `int` `MaximumProduct(``int` `N,``                              ``List > Edge,``                              ``List<``int``> wt)``    ``{``        ``// Stores the count of edges``        ``int` `M = wt.Count;` `        ``// Stores all the edges mapped``        ``// with a particular weight``        ``Dictionary<``int``, List > > mp``            ``= ``new` `Dictionary<``int``,``                             ``List > >();` `        ``// Update the map mp``        ``for` `(``int` `i = 0; i < M; i++) {``            ``if` `(!mp.ContainsKey(wt[i])) {``                ``mp.Add(wt[i], ``new` `List >());``            ``}``            ``mp[wt[i]].Add(Edge[i]);``        ``}` `        ``var` `keys = mp.Keys.ToList();``        ``keys.Sort();``        ``keys.Reverse();` `        ``// Stores the result``        ``int` `res = 0;` `        ``// Traverse the map mp``        ``foreach``(``var` `i ``in` `keys)``        ``{` `            ``// Stores the adjacency list``            ``List > adj = ``new` `List >();``            ``for` `(``int` `j = 0; j <= N; j++)``                ``adj.Add(``new` `List<``int``>());` `            ``// Stores the edges of``            ``// a particular weight``            ``List > v = mp[i];` `            ``// Traverse the vector v``            ``for` `(``int` `j = 0; j < v.Count; j++) {` `                ``int` `U = v[j].Item1;``                ``int` `V = v[j].Item2;` `                ``// Add an edge``                ``adj[U].Add(V);``                ``adj[V].Add(U);``            ``}` `            ``// Stores if a vertex``            ``// is visited or not``            ``List<``bool``> vis = ``new` `List<``bool``>();``            ``for` `(``int` `j = 0; j <= N; j++)``                ``vis.Add(``false``);` `            ``// Stores the maximum``            ``// size of a component``            ``int` `cntMax = 0;` `            ``// Iterate over the range [1, N]``            ``for` `(``int` `u = 1; u <= N; u++) {` `                ``// Assign Max, sMax, count = 0``                ``Max = 0;``                ``sMax = 0;``                ``cnt = 0;` `                ``// If vertex u is not visited``                ``if` `(!vis[u]) {` `                    ``dfs(u, N, vis, adj);` `                    ``// If cnt is greater``                    ``// than cntMax``                    ``if` `(cnt > cntMax) {` `                        ``// Update the res``                        ``res = Max * sMax;``                        ``cntMax = cnt;``                    ``}` `                    ``// If already largest``                    ``// connected component``                    ``else` `if` `(cnt == cntMax) {` `                        ``// Update res``                        ``res = Math.Max(res, Max * sMax);``                    ``}``                ``}``            ``}``        ``}` `        ``// Return res``        ``return` `res;``    ``}` `    ``// Driver Code``    ``public` `static` `void` `Main(``string``[] args)``    ``{``        ``int` `N = 5;``        ``List > Edges``            ``= ``new` `List >();``        ``Edges.Add(Tuple.Create(1, 2));``        ``Edges.Add(Tuple.Create(2, 5));``        ``Edges.Add(Tuple.Create(3, 5));``        ``Edges.Add(Tuple.Create(4, 5));``        ``Edges.Add(Tuple.Create(1, 2));``        ``Edges.Add(Tuple.Create(2, 3));``        ``Edges.Add(Tuple.Create(3, 4));` `        ``List<``int``> Weight``            ``= ``new` `List<``int``>{ 1, 1, 1, 1, 2, 2, 2 };``        ``Console.WriteLine(MaximumProduct(N, Edges, Weight));``    ``}``}` `// This code is contributed by phasing17`

Output:

`20`

Time Complexity: O(N2 * log N + M)
Auxiliary Space: O(N2)