Minimum path need to reverse to reach each node in a tree from each vertex (original) (raw)

Last Updated : 23 Jul, 2025

Given a directed tree consisting of N nodes valued from [0, N - 1] and M edges, the task is to find the minimum number of edges that need to reverse for each node X such that there is a path from node X to each vertex of the given Tree.

Examples:

Input: N = 6, edges[][] = {{0, 1}, {1, 3}, {2, 3}, {4, 0}, {4, 5}}
Output: 2 2 2 3 1 2
Explanation:
The answer for node 0 is 2, which can be calculated as:

From 0 to 0: No edges are required to reverse to reach 0 from 0.
From 0 to 1: Can be reached directly using edge 0 -> 1.
From 0 to 2: The edge 2 -> 3 must be reversed for the path 0 -> 1 -> 3 -> 2 to reach 2 from node 0.
From 0 to 3: Can be reached directly as 0 -> 1 -> 3.
From 0 to 4: The edge 4 -> 0 must be reversed to reach 4 from node 0.
From 0 to 5: The edge 4 -> 0 must be reversed to reach 5 from node 0 as 0 -> 4 -> 5

To reach every node from the node 0, edge 2 -> 3 and edge 4 -> 0 is reversed. So, a total of 2 edges is reversed for node 0. Similarly, the ans for all the nodes can be calculated.

Input: N = 5, edges[][] = {{1, 0}, {1, 2}, {3, 2}, {3, 4}}
Output: 2 1 2 1 2

Approach: To solve the above problem, the idea is to store the directed edge in the adjacency list along with the reversed directed edge with the negative sign i.e. for directed edge a -> b store the edge a -> b and b -> -a. Then, for each node X of the tree, the answer can be calculated as the number of negative edges encountered in the simple Depth For Search(DFS) from that node X.Follow the steps below to solve the problem:

Below is the implementation of the above approach:

C++ `

// C++ program for the above approach

#include <bits/stdc++.h> using namespace std;

// Function to perform the DFS traversal // of the tree with reordered paths void reorderPaths( int s, vector<vector > graph, int& count, vector& visited) { visited[s] = true;

// Traverse the adjacency list of
// the source node
for (auto i : graph[s]) {

    if (!visited[abs(i)]) {

        // Reorder the path
        if (i < 0)
            count++;

        // Recursively Call DFS
        reorderPaths(abs(i), graph,
                     count, visited);
    }
}

}

// Function to find minimum edges to // reverse to make the tree vertices // reachable for each node void minReorder(int n, vector<vector > edges) { // Stores the edges vector<vector > graph(n);

// Traversing the childs
for (int i = 0; i < edges.size(); i++) {
    int a = edges[i][0];
    int b = edges[i][1];

    // Storing the direct edge
    graph[a].push_back(b);

    // Storing the reverse edge
    graph[b].push_back(-a);
}

// Finding ans for each node
for (int i = 0; i < n; i++) {
    vector<bool> visited(n, false);
    int count = 0;

    // Function Call
    reorderPaths(i, graph, count, visited);
    cout << count << " ";
}

}

// Driver Code int main() { int N = 6; vector<vector > edges = { { 0, 1 }, { 1, 3 }, { 2, 3 }, { 4, 0 }, { 4, 5 } }; minReorder(N, edges);

return 0;

}

Java

// Java program for the above approach import java.util.*;

public class GFG{ static int count;

// Function to perform the DFS traversal // of the tree with reordered paths static void reorderPaths( int s, Vector[] graph, boolean[] visited) { visited[s] = true;

// Traverse the adjacency list of
// the source node
for (int i : graph[s]) {

    if (!visited[(Math.abs(i))]) {

        // Reorder the path
        if (i < 0)
            count++;

        // Recursively Call DFS
        reorderPaths(Math.abs(i), graph, visited);
    }
}

}

// Function to find minimum edges to // reverse to make the tree vertices // reachable for each node static void minReorder(int n, int [][] edges) {

// Stores the edges
Vector<Integer>[] graph = new Vector[n];
for (int i = 0; i < n; i++) 
    graph[i] = new Vector<>();

// Traversing the childs
for (int i = 0; i < edges.length; i++) {

    int a = edges[i][0];
    int b = edges[i][1];

    // Storing the direct edge
    graph[a].add(b);

    // Storing the reverse edge
    graph[b].add(-a);
}

// Finding ans for each node
for (int i = 0; i < n; i++) {
    boolean []visited = new boolean[n];
    count = 0;

    // Function Call
    reorderPaths(i, graph,  visited);
    System.out.print(count+ " ");
}

}

// Driver Code public static void main(String[] args) { int N = 6; int [][] edges = { { 0, 1 }, { 1, 3 }, { 2, 3 }, { 4, 0 }, { 4, 5 } }; minReorder(N, edges);

} }

// This code is contributed by 29AjayKumar

Python3

Python 3 program for the above approach

count = 0 visited = []

Function to perform the DFS traversal

of the tree with reordered paths

def reorderPaths(s, graph): global count visited[s] = True

# Traverse the adjacency list of
# the source node
for i in graph[s]:
    if(visited[abs(i)]==False):
        # Reorder the path
        if (i < 0):
            count += 1

        # Recursively Call DFS
        reorderPaths(abs(i), graph)

Function to find minimum edges to

reverse to make the tree vertices

reachable for each node

def minReorder(n, edges): global count global visited # Stores the edges graph = [[] for i in range(n)]

# Traversing the childs
for i in range(len(edges)):
    a = edges[i][0]
    b = edges[i][1]

    # Storing the direct edge
    graph[a].append(b)

    # Storing the reverse edge
    graph[b].append(-a)

# Finding ans for each node
for i in range(n):
    visited = [False for i in range(n)]
    count = 0

    # Function Call
    reorderPaths(i, graph)
    print(count,end = " ")

Driver Code

if name == 'main': N = 6 edges = [[0, 1],[1, 3],[2, 3],[4, 0],[4, 5]] minReorder(N, edges)

# This code is contributed by SURENDRA_GANGWAR.

C#

// C# code for above approach using System; using System.Collections.Generic;

public class GFG { static int count;

// Function to perform the DFS traversal
// of the tree with reordered paths
static void ReorderPaths(int s, List<int>[] graph,
                         bool[] visited)
{
    visited[s] = true;

    // Traverse the adjacency list of
    // the source node
    foreach(int i in graph[s])
    {

        if (!visited[(Math.Abs(i))]) {

            // Reorder the path
            if (i < 0)
                count++;

            // Recursively Call DFS
            ReorderPaths(Math.Abs(i), graph, visited);
        }
    }
}

// Function to find minimum edges to
// reverse to make the tree vertices
// reachable for each node
static void MinReorder(int n, int[][] edges)
{

    // Stores the edges
    List<int>[] graph = new List<int>[ n ];
    for (int i = 0; i < n; i++)
        graph[i] = new List<int>();

    // Traversing the childs
    for (int i = 0; i < edges.Length; i++) {

        int a = edges[i][0];
        int b = edges[i][1];

        // Storing the direct edge
        graph[a].Add(b);

        // Storing the reverse edge
        graph[b].Add(-a);
    }

    // Finding ans for each node
    for (int i = 0; i < n; i++) {
        bool[] visited = new bool[n];
        count = 0;

        // Function Call
        ReorderPaths(i, graph, visited);
        Console.Write(count + " ");
    }
}

// Driver Code
public static void Main(string[] args)
{
    int N = 6;
    int[][] edges
        = { new int[] { 0, 1 }, new int[] { 1, 3 },
            new int[] { 2, 3 }, new int[] { 4, 0 },
            new int[] { 4, 5 } };

    MinReorder(N, edges);
}

}

// This code is contributed by Vaibhav.

JavaScript

`

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