Iterative Depth First Traversal of Graph

Depth First Traversal (or Search) for a graph is similar to Depth First Traversal (DFS) of a tree. The only catch here is, unlike trees, graphs may contain cycles, so we may come to the same node again. To avoid processing a node more than once, we use a boolean visited array.

For example, a DFS of below graph is “0 3 4 2 1”, other possible DFS is “0 2 1 3 4”.

We have discussed recursive implementation of DFS in previous in previous post. In the post, iterative DFS is discussed. The recursive implementation uses function call stack. In iterative implementation, an explicit stack is used to hold visited vertices.

Below is implementation of Iterative DFS. The implementation is similar to BFS, the only difference is queue is replaced by stack.



C++

filter_none

edit
close

play_arrow

link
brightness_4
code

// An Iterative C++ program to do DFS traversal from
// a given source vertex. DFS(int s) traverses vertices
// reachable from s.
#include<bits/stdc++.h>
using namespace std;
  
// This class represents a directed graph using adjacency
// list representation
class Graph
{
    int V;    // No. of vertices
    list<int> *adj;    // adjacency lists
public:
    Graph(int V);  // Constructor
    void addEdge(int v, int w); // to add an edge to graph
    void DFS(int s);  // prints all vertices in DFS manner
    // from a given source.
};
  
Graph::Graph(int V)
{
    this->V = V;
    adj = new list<int>[V];
}
  
void Graph::addEdge(int v, int w)
{
    adj[v].push_back(w); // Add w to v’s list.
}
  
// prints all not yet visited vertices reachable from s
void Graph::DFS(int s)
{
    // Initially mark all verices as not visited
    vector<bool> visited(V, false);
  
    // Create a stack for DFS
    stack<int> stack;
  
    // Push the current source node.
    stack.push(s);
  
    while (!stack.empty())
    {
        // Pop a vertex from stack and print it
        s = stack.top();
        stack.pop();
  
        // Stack may contain same vertex twice. So
        // we need to print the popped item only
        // if it is not visited.
        if (!visited[s])
        {
            cout << s << " ";
            visited[s] = true;
        }
  
        // Get all adjacent vertices of the popped vertex s
        // If a adjacent has not been visited, then puah it
        // to the stack.
        for (auto i = adj[s].begin(); i != adj[s].end(); ++i)
            if (!visited[*i])
                stack.push(*i);
    }
}
  
// Driver program to test methods of graph class
int main()
{
    Graph g(5); // Total 5 vertices in graph
    g.addEdge(1, 0);
    g.addEdge(0, 2);
    g.addEdge(2, 1);
    g.addEdge(0, 3);
    g.addEdge(1, 4);
  
    cout << "Following is Depth First Traversal\n";
    g.DFS(0);
  
    return 0;
}

chevron_right


Java

filter_none

edit
close

play_arrow

link
brightness_4
code

//An Iterative Java program to do DFS traversal from
//a given source vertex. DFS(int s) traverses vertices
//reachable from s.
  
import java.util.*;
  
public class GFG 
{
    // This class represents a directed graph using adjacency
    // list representation
    static class Graph
    {
        int V; //Number of Vertices
          
        LinkedList<Integer>[] adj; // adjacency lists
          
        //Constructor
        Graph(int V)
        {
            this.V = V;
            adj = new LinkedList[V];
              
            for (int i = 0; i < adj.length; i++)
                adj[i] = new LinkedList<Integer>();
              
        }
          
        //To add an edge to graph
        void addEdge(int v, int w)
        {
            adj[v].add(w); // Add w to v’s list.
        }
          
        // prints all not yet visited vertices reachable from s
        void DFS(int s)
        {
            // Initially mark all vertices as not visited
            Vector<Boolean> visited = new Vector<Boolean>(V);
            for (int i = 0; i < V; i++)
                visited.add(false);
      
            // Create a stack for DFS
            Stack<Integer> stack = new Stack<>();
              
            // Push the current source node
            stack.push(s);
              
            while(stack.empty() == false)
            {
                // Pop a vertex from stack and print it
                s = stack.peek();
                stack.pop();
                  
                // Stack may contain same vertex twice. So
                // we need to print the popped item only
                // if it is not visited.
                if(visited.get(s) == false)
                {
                    System.out.print(s + " ");
                    visited.set(s, true);
                }
                  
                // Get all adjacent vertices of the popped vertex s
                // If a adjacent has not been visited, then puah it
                // to the stack.
                Iterator<Integer> itr = adj[s].iterator();
                  
                while (itr.hasNext()) 
                {
                    int v = itr.next();
                    if(!visited.get(v))
                        stack.push(v);
                }
                  
            }
        }
    }
      
    // Driver program to test methods of graph class
    public static void main(String[] args) 
    {
        // Total 5 vertices in graph
        Graph g = new Graph(5);
          
        g.addEdge(1, 0);
        g.addEdge(0, 2);
        g.addEdge(2, 1);
        g.addEdge(0, 3);
        g.addEdge(1, 4);
              
        System.out.println("Following is the Depth First Traversal");
        g.DFS(0);
    }
}

chevron_right


Output:

Following is Depth First Traversal
0 3 2 1 4 

Note that the above implementation prints only vertices that are reachable from a given vertex. For example, if we remove edges 0-3 and 0-2, the above program would only print 0. To print all vertices of a graph, we need to call DFS for every vertex. Below is implementation for the same.

C++

filter_none

edit
close

play_arrow

link
brightness_4
code

// An Iterative C++ program to do DFS traversal from
// a given source vertex. DFS(int s) traverses vertices
// reachable from s.
#include<bits/stdc++.h>
using namespace std;
  
// This class represents a directed graph using adjacency
// list representation
class Graph
{
    int V;    // No. of vertices
    list<int> *adj;    // adjacency lists
public:
    Graph(int V);  // Constructor
    void addEdge(int v, int w); // to add an edge to graph
    void DFS();  // prints all vertices in DFS manner
  
    // prints all not yet visited vertices reachable from s
    void DFSUtil(int s, vector<bool> &visited);
};
  
Graph::Graph(int V)
{
    this->V = V;
    adj = new list<int>[V];
}
  
void Graph::addEdge(int v, int w)
{
    adj[v].push_back(w); // Add w to v’s list.
}
  
// prints all not yet visited vertices reachable from s
void Graph::DFSUtil(int s, vector<bool> &visited)
{
    // Create a stack for DFS
    stack<int> stack;
  
    // Puah the current source node.
    stack.push(s);
  
    while (!stack.empty())
    {
        // Pop a vertex from stack and print it
        s = stack.top();
        stack.pop();
  
        // Stack may contain same vertex twice. So
        // we need to print the popped item only
        // if it is not visited.
        if (!visited[s])
        {
            cout << s << " ";
            visited[s] = true;
        }
  
        // Get all adjacent vertices of the popped vertex s
        // If a adjacent has not been visited, then puah it
        // to the stack.
        for (auto i = adj[s].begin(); i != adj[s].end(); ++i)
            if (!visited[*i])
                stack.push(*i);
    }
}
  
// prints all vertices in DFS manner
void Graph::DFS()
{
    // Mark all the vertices as not visited
    vector<bool> visited(V, false);
  
    for (int i = 0; i < V; i++)
        if (!visited[i])
            DFSUtil(i, visited);
}
  
// Driver program to test methods of graph class
int main()
{
    Graph g(5);  // Total 5 vertices in graph
    g.addEdge(1, 0);
    g.addEdge(2, 1);
    g.addEdge(3, 4);
    g.addEdge(4, 0);
  
    cout << "Following is Depth First Traversal\n";
    g.DFS();
  
    return 0;
}

chevron_right


Java

filter_none

edit
close

play_arrow

link
brightness_4
code

//An Iterative Java program to do DFS traversal from
//a given source vertex. DFS() traverses vertices
//reachable from s.
  
import java.util.*;
  
public class GFG 
{
    // This class represents a directed graph using adjacency
    // list representation
    static class Graph
    {
        int V; //Number of Vertices
          
        LinkedList<Integer>[] adj; // adjacency lists
          
        //Constructor
        Graph(int V)
        {
            this.V = V;
            adj = new LinkedList[V];
              
            for (int i = 0; i < adj.length; i++)
                adj[i] = new LinkedList<Integer>();
              
        }
          
        //To add an edge to graph
        void addEdge(int v, int w)
        {
            adj[v].add(w); // Add w to v’s list.
        }
          
        // prints all not yet visited vertices reachable from s
        void DFSUtil(int s, Vector<Boolean> visited)
        {
            // Create a stack for DFS
            Stack<Integer> stack = new Stack<>();
               
            // Push the current source node
            stack.push(s);
               
            while(stack.empty() == false)
            {
                // Pop a vertex from stack and print it
                s = stack.peek();
                stack.pop();
                   
                // Stack may contain same vertex twice. So
                // we need to print the popped item only
                // if it is not visited.
                if(visited.get(s) == false)
                {
                    System.out.print(s + " ");
                    visited.set(s, true);
                }
                   
                // Get all adjacent vertices of the popped vertex s
                // If a adjacent has not been visited, then puah it
                // to the stack.
                Iterator<Integer> itr = adj[s].iterator();
                   
                while (itr.hasNext()) 
                {
                    int v = itr.next();
                    if(!visited.get(v))
                        stack.push(v);
                }
                   
            }
        }
          
        // prints all vertices in DFS manner
        void DFS()
        {
            Vector<Boolean> visited = new Vector<Boolean>(V);
            // Mark all the vertices as not visited
            for (int i = 0; i < V; i++)
                visited.add(false);
      
            for (int i = 0; i < V; i++)
                if (!visited.get(i))
                    DFSUtil(i, visited);
        }    
    }
      
    // Driver program to test methods of graph class
    public static void main(String[] args) 
    {
        Graph g = new Graph(5);
        g.addEdge(1, 0);
        g.addEdge(2, 1);
        g.addEdge(3, 4);
        g.addEdge(4, 0);
           
        System.out.println("Following is Depth First Traversal");
        g.DFS();
    }
}

chevron_right



Output:

Following is Depth First Traversal
0 1 2 3 4

Like recursive traversal, time complexity of iterative implementation is O(V + E).

This article is contributed by Shivam. Please write comments if you find anything incorrect, or you want to share more information about the topic discussed above.



My Personal Notes arrow_drop_up


Article Tags :
Practice Tags :


1


Please write to us at contribute@geeksforgeeks.org to report any issue with the above content.