# Count pairs of vertices in Tree such that distance between them is even

• Difficulty Level : Hard
• Last Updated : 06 Jun, 2022

Given a tree of N vertices, the task is to find the number of pairs of vertices such that the distance between them is even but cannot be 0

Examples:

Input: N = 5, Edges = [ [1, 0], [2, 1], [3, 1], [4, 3] ]

0
/
1
/    \
2        3
\
4

Output: 4
Explanation: There are four pairs of vertices such that the distance between them is even.
They are [ 0, 2 ], [0, 3], [3, 2] and [1, 4].

Input: N = 6, Edges: [[1, 0], [2, 1], [3, 1], [4, 2], [5, 3]]

0
/
1
/       \
2            3
/             /
4              5
Output: 6
Explanation: There are 6 pairs of vertices such that the distance between them is even. They are [0, 2], [4, 1], [3, 0], [4, 5], [1, 5] and [2, 3].

Naive Approach: The naive approach is to try all possible pairs of vertices, find the distance between them and check if the distance is even. Follow the steps mentioned below to solve the problem:

• Iterate over all the vertices for i = 0 to N-1:
• Iterate from j = i+1 to N-1:
• Find the distance from i to j using DFS.
• If the distance is even then increment the count of pairs.
• Return the count.

Below is the implementation of the above approach.

## C++

 `// C++ code to implement the approach`   `#include ` `using` `namespace` `std;`   `// Function to find the distance` `void` `dfs(``int` `i, ``int` `par,` `         ``vector >& adj,` `         ``vector<``int``>& dis)` `{` `    ``// Iterate over all the edges of vertex i` `    ``for` `(``int` `j : adj[i]) {`   `        ``// If 'j' is not the parent of 'i'.` `        ``if` `(j != par) {`   `            ``// Store the distance` `            ``// from root till 'j'.` `            ``dis[j] = dis[i] + 1;`   `            ``// Recurse for the child 'j'.` `            ``dfs(j, i, adj, dis);` `        ``}` `    ``}` `}`   `// Function to count pairs` `int` `countPairs(``int` `n,` `               ``vector >& edges)` `{` `    ``// Stores the final answer.` `    ``int` `ans = 0;`   `    ``// Stores the adjacency List of the tree.` `    ``vector > adj(n);`   `    ``for` `(``int` `i = 0; i < n - 1; ++i) {`   `        ``// Add the edge in the adjacency list.` `        ``adj[edges[i]].push_back(edges[i]);` `        ``adj[edges[i]].push_back(edges[i]);` `    ``}`   `    ``// Stores the distance from root till 'i'.` `    ``vector<``int``> dis(n);`   `    ``// Iterate over all 'u'` `    ``// of the pair ('u', 'v').` `    ``for` `(``int` `i = 0; i < n; ++i) {`   `        ``// Set all the values` `        ``// of 'dis[i]' to '0'.` `        ``fill(dis.begin(), dis.end(), 0);`   `        ``// Do a dfs with 'i' as` `        ``// the root of the tree.` `        ``dfs(i, -1, adj, dis);`   `        ``// Iterate over the other end` `        ``// of the pair.` `        ``for` `(``int` `j = i + 1; j < n; ++j) {`   `            ``// If the distance is even.` `            ``if` `(dis[j] % 2 == 0) {`   `                ``// Increment 'ans' by 1.` `                ``ans++;` `            ``}` `        ``}` `    ``}`   `    ``// Return the answer 'ans'.` `    ``return` `ans;` `}`   `// Driver Code` `int` `main()` `{` `    ``int` `N = 5;` `    ``vector > edges` `        ``= { { 1, 0 }, { 2, 1 }, { 3, 1 }, { 4, 3 } };`   `    ``// Function call` `    ``cout << countPairs(N, edges);` `    ``return` `0;` `}`

## Java

 `// Java code to implement above approach` `import` `java.util.*;`   `public` `class` `Main` `{`   `  ``// Function to find the distance` `  ``static` `void` `dfs(``int` `i, ``int` `par,` `                  ``ArrayList > adj,` `                  ``ArrayList dis)` `  ``{` `    ``// Iterate over all the edges of vertex i` `    ``for` `(``int` `j : adj.get(i) ) {`   `      ``// If 'j' is not the parent of 'i'.` `      ``if` `(j != par) {`   `        ``// Store the distance` `        ``// from root till 'j'.` `        ``dis.set(j, dis.get(i) + ``1``);`   `        ``// Recurse for the child 'j'.` `        ``dfs(j, i, adj, dis);` `      ``}` `    ``}` `  ``}`   `  ``// Function to count pairs` `  ``static` `int` `countPairs(``int` `n,` `                        ``int``[][] edges)` `  ``{` `    ``// Stores the final answer.` `    ``int` `ans = ``0``;`   `    ``// Stores the adjacency List of the tree.` `    ``ArrayList > adj = ` `      ``new` `ArrayList >(n);` `    ``for` `(``int` `i = ``0``; i < n; i++)` `      ``adj.add(``new` `ArrayList());`   `    ``for` `(``int` `i = ``0``; i < n - ``1``; ++i) {`   `      ``// Add the edge in the adjacency list.` `      ``adj.get(edges[i][``0``]).add(edges[i][``1``]);` `      ``adj.get(edges[i][``1``]).add(edges[i][``0``]);` `    ``}`   `    ``// Iterate over all 'u'` `    ``// of the pair ('u', 'v').` `    ``for` `(``int` `i = ``0``; i < n; ++i) {`   `      ``ArrayList dis =` `        ``new` `ArrayList (n);;` `      ``// Do a dfs with 'i' as` `      ``// the root of the tree.` `      ``for` `(``int` `j = ``0``; j < n; ++j) {` `        ``dis.add(``0``);` `      ``}` `      ``dfs(i, -``1``, adj, dis);`   `      ``// Iterate over the other end` `      ``// of the pair.` `      ``for` `(``int` `j = i + ``1``; j < n; ++j) {`   `        ``// If the distance is even.` `        ``if` `(dis.get(j) % ``2` `== ``0``) {`   `          ``// Increment 'ans' by 1.` `          ``ans++;` `        ``}` `      ``}` `    ``}`   `    ``// Return the answer 'ans'.` `    ``return` `ans;` `  ``}` `  ``// Driver Code ` `  ``public` `static` `void` `main(String args[])` `  ``{` `    ``int` `N = ``5``;`   `    ``// array of edges` `    ``int``[][] edges` `      ``= { { ``1``, ``0` `}, { ``2``, ``1` `}, { ``3``, ``1` `}, { ``4``, ``3` `} };`   `    ``// Function call` `    ``System.out.println( countPairs(N, edges) );`   `  ``}` `}`   `// This code is contributed by Sachin Sahara (sachin801)`

## Javascript

 ``

Output

`4`

Time Complexity: O(N2)
Auxiliary Space: O(N)

Efficient Approach: The efficient approach to solve the problem is based on the concept of bipartite graph as shown below.

Every tree is a bipartite graph. So all the vertices are part of one of the two bipartite sets (say L and R).
Any pair having both the values from different sets have an odd distance between them and pairs with vertices from the same set have even distance between them.

Based on the above observation it is clear that the total number of pairs is the possible pairs formed using vertices from the same set i.e., (xC2) + (yC2), where [ nC2 = n * (n – 1)/2, x is the size of set L and y is the size of set R ]. Follow the steps mentioned below to solve the problem.

• Declare and initialize two variables x and y to 0 to store the size of the bipartite sets.
• Make root a part of one of the bipartite set (say L).
• Initialize an array (say dis[]) to store the distances from 0.
• Start a DFS or BFS from the vertex 0:
• At each instant, iterate through all the children, and if we have not visited this child yet (let’s say the child is j), then:
• Increment its distance as dis[current node] = distance[parent] + 1.
• If it is even, increment x and make it part of set L. Otherwise, increment y and make it part of set R.
• Recursively do the same for its children.
• Finally, return the value of xC2 + yC2.

Below is the implementation of the above approach.

## C++

 `// C++ code to implement the approach`   `#include ` `using` `namespace` `std;`   `// Dfs function` `void` `dfs(``int` `i, ``int` `par,` `         ``vector >& adj,` `         ``vector<``int``>& dis)` `{` `    ``// Iterate over all edges of vertex 'i'.` `    ``for` `(``int` `j : adj[i]) {`   `        ``// If 'j' is not the parent of 'i'.` `        ``if` `(j != par) {`   `            ``// Store the distance` `            ``// from root till 'j'.` `            ``dis[j] = dis[i] + 1;`   `            ``// Recurse for the child 'j'.` `            ``dfs(j, i, adj, dis);` `        ``}` `    ``}` `}`   `// Function to count the vertices` `int` `countPairs(``int` `n,` `               ``vector >& edges)` `{` `    ``// Stores the adjacency List of the tree.` `    ``vector > adj(n);` `    ``for` `(``int` `i = 0; i < n - 1; ++i) {`   `        ``// Add the edge in the adjacency list.` `        ``adj[edges[i]].push_back(edges[i]);` `        ``adj[edges[i]].push_back(edges[i]);` `    ``}`   `    ``// Stores the distance from root till 'i'.` `    ``vector<``int``> dis(n);`   `    ``// Dfs with '0' as the root of the tree.` `    ``dfs(0, -1, adj, dis);`   `    ``// To store the size of set 'L'` `    ``// size of set 'R'.` `    ``int` `x = 0, y = 0;`   `    ``// Iterate over all the vertices` `    ``// of the tree.` `    ``for` `(``int` `i = 0; i < n; ++i) {`   `        ``// If 'i' is at an even depth.` `        ``if` `(dis[i] % 2 == 0) {`   `            ``// Increment the size of set 'L'.` `            ``x++;` `        ``}` `        ``else` `{`   `            ``// Increment the size of set 'R'.` `            ``y++;` `        ``}` `    ``}`   `    ``// Return the answer.` `    ``return` `x * (x - 1) / 2 + y * (y - 1) / 2;` `}`   `// Driver Code` `int` `main()` `{` `    ``int` `N = 5;` `    ``vector > edges` `        ``= { { 1, 0 }, { 2, 1 }, { 3, 1 }, { 4, 3 } };`   `    ``// Function call` `    ``cout << countPairs(N, edges);` `    ``return` `0;` `}`

## Java

 `// Java code to implement above approach`   `import` `java.util.*;`   `public` `class` `Main {` `    ``// Function to find the distance` `    ``static` `void` `dfs(``int` `i, ``int` `par,` `            ``ArrayList > adj,` `            ``ArrayList dis)` `    ``{` `        ``// Iterate over all the edges of vertex i` `        ``for` `(``int` `j : adj.get(i) ) {`   `            ``// If 'j' is not the parent of 'i'.` `            ``if` `(j != par) {`   `                ``// Store the distance` `                ``// from root till 'j'.` `                ``dis.set(j, dis.get(i) + ``1``);`   `                ``// Recurse for the child 'j'.` `                ``dfs(j, i, adj, dis);` `            ``}` `        ``}` `    ``}`   `    ``// Function to count pairs` `    ``static` `int` `countPairs(``int` `n,` `                ``int``[][] edges)` `    ``{` `        ``// Stores the adjacency List of the tree.` `        ``ArrayList > adj = ` `                        ``new` `ArrayList >(n);` `        ``for` `(``int` `i = ``0``; i < n; i++)` `            ``adj.add(``new` `ArrayList());`   `        ``for` `(``int` `i = ``0``; i < n - ``1``; ++i) {`   `            ``// Add the edge in the adjacency list.` `            ``adj.get(edges[i][``0``]).add(edges[i][``1``]);` `            ``adj.get(edges[i][``1``]).add(edges[i][``0``]);` `        ``}`   `        ``// Stores the distance from root till 'i'.` `        ``ArrayList dis = ``new` `ArrayList (n);` `        ``for` `(``int` `j = ``0``; j < n; ++j) {` `            ``dis.add(``0``);` `        ``}` `        ``// Dfs with '0' as the root of the tree.` `        ``dfs(``0``, -``1``, adj, dis);`   `        ``// To store the size of set 'L'` `        ``// size of set 'R'.` `        ``int` `x = ``0``, y = ``0``;`   `        ``// Iterate over all the vertices` `        ``// of the tree.` `        ``for` `(``int` `i = ``0``; i < n; ++i) {`   `            ``// If 'i' is at an even depth.` `            ``if` `(dis.get(i) % ``2` `== ``0``) {`   `                ``// Increment the size of set 'L'.` `                ``x++;` `            ``}` `            ``else` `{`   `                ``// Increment the size of set 'R'.` `                ``y++;` `            ``}` `        ``}`   `        ``// Return the answer.` `        ``return` `x * (x - ``1``) / ``2` `+ y * (y - ``1``) / ``2``;` `    ``}`   `    ``// Driver Code ` `    ``public` `static` `void` `main(String args[]) {` `        ``int` `N = ``5``;` `        ``// array of edges` `        ``int``[][] edges` `            ``= { { ``1``, ``0` `}, { ``2``, ``1` `}, { ``3``, ``1` `}, { ``4``, ``3` `} };`   `        ``// Function call` `        ``System.out.println( countPairs(N, edges) );` `        `  `    ``}` `}`   `// This code is contributed by Sachin Sahara (sachin801)`

## Python3

 `# python3 code to implement the approach`   `# Dfs function` `def` `dfs(i, par, adj, dis):`   `    ``# Iterate over all edges of vertex 'i'.` `    ``for` `j ``in` `adj[i]:`   `        ``# If 'j' is not the parent of 'i'.` `        ``if` `(j !``=` `par):`   `            ``# Store the distance` `            ``# from root till 'j'.` `            ``dis[j] ``=` `dis[i] ``+` `1`   `            ``# Recurse for the child 'j'.` `            ``dfs(j, i, adj, dis)`   `# Function to count the vertices` `def` `countPairs(n, edges):`   `    ``# Stores the adjacency List of the tree.` `    ``adj ``=` `[[] ``for` `_ ``in` `range``(n)]` `    ``for` `i ``in` `range``(``0``, n``-``1``):`   `        ``# Add the edge in the adjacency list.` `        ``adj[edges[i][``0``]].append(edges[i][``1``])` `        ``adj[edges[i][``1``]].append(edges[i][``0``])`   `    ``# Stores the distance from root till 'i'.` `    ``dis ``=` `[``0` `for` `_ ``in` `range``(n)]`   `    ``# Dfs with '0' as the root of the tree.` `    ``dfs(``0``, ``-``1``, adj, dis)`   `    ``# To store the size of set 'L'` `    ``# size of set 'R'.` `    ``x, y ``=` `0``, ``0`   `    ``# Iterate over all the vertices` `    ``# of the tree.` `    ``for` `i ``in` `range``(``0``, n):`   `        ``# If 'i' is at an even depth.` `        ``if` `(dis[i] ``%` `2` `=``=` `0``):`   `            ``# Increment the size of set 'L'.` `            ``x ``+``=` `1`   `        ``else``:`   `            ``# Increment the size of set 'R'.` `            ``y ``+``=` `1`   `    ``# Return the answer.` `    ``return` `x ``*` `(x ``-` `1``) ``/``/` `2` `+` `y ``*` `(y ``-` `1``) ``/``/` `2`     `# Driver Code` `if` `__name__ ``=``=` `"__main__"``:`   `    ``N ``=` `5` `    ``edges ``=` `[[``1``, ``0``], [``2``, ``1``], [``3``, ``1``], [``4``, ``3``]]`   `    ``# Function call` `    ``print``(countPairs(N, edges))`   `# This code is contributed by rakeshsahni`

Output

`4`

Time Complexity: O(N)
Auxiliary Space: O(N)

My Personal Notes arrow_drop_up
Recommended Articles
Page :