Kosaraju’s Algorithm in C++
Last Updated : 23 Jul, 2025
In this post, we will see the implementation of Kosaraju’s Algorithm in C++.
Kosaraju’s Algorithm is a classic algorithm used for finding strongly connected components (SCCs) in a directed graph. An SCC is a maximal subgraph where every vertex is reachable from every other vertex in the subgraph. This algorithm is widely used in various applications such as finding cycles in a graph, circuit design, and network analysis.
Below is an example of a strongly connected graph:
Strongly connectedHow does Kosaraju’s Algorithm Work in C++?
The algorithm works in two main phases:
- Perform a Depth-First Search (DFS) on the original graph and store the vertices in a stack according to their finish times.
- Transpose (reverse) the graph and perform DFS using the vertices in the order defined by the stack to identify the SCCs.
Steps of Kosaraju’s Algorithm to Implement in C++
Following are steps of Kosaraju’s DFS-based simple algorithm that does two DFS traversals of the graph:
- Initialize all vertices as not visited.
- Do a DFS traversal of graph starting from any arbitrary vertex v. If DFS traversal doesn’t visit all vertices, then return false.
- Reverse all arcs (or find transpose or reverse of graph)
- Mark all vertices as not-visited in reversed graph.
- Do a DFS traversal of reversed graph starting from same vertex v (Same as step 2). If DFS traversal doesn’t visit all vertices, then return false. Otherwise return true.
C++ Program to Implement Kosaraju’s Algorithm
Below is a C++ program that implements Kosaraju’s Algorithm for finding strongly connected components:
C++ // C++ program to implement Kosaraju’s algorithm to check if // a given directed graph is strongly connected or not #include <iostream> #include <list> #include <stack> using namespace std; class Graph { // No. of vertices int V; // An array of adjacency lists list<int>* adj; // A recursive function to print DFS // starting from v void DFSUtil(int v, bool visited[]); public: // Constructor and Destructor Graph(int V) { this->V = V; adj = new list<int>[V]; } ~Graph() { delete[] adj; } // Method to add an edge void addEdge(int v, int w); // The main function that returns true if the // graph is strongly connected, otherwise false bool isSC(); // Function that returns reverse (or transpose) // of this graph Graph getTranspose(); }; // A recursive function to print DFS starting from v void Graph::DFSUtil(int v, bool visited[]) { // Mark the current node as visited and print it visited[v] = true; // Recur for all the vertices adjacent to this vertex list<int>::iterator i; for (i = adj[v].begin(); i != adj[v].end(); ++i) if (!visited[*i]) DFSUtil(*i, visited); } // Function that returns reverse (or transpose) of this // graph Graph Graph::getTranspose() { Graph g(V); for (int v = 0; v < V; v++) { // Recur for all the vertices adjacent to this // vertex list<int>::iterator i; for (i = adj[v].begin(); i != adj[v].end(); ++i) { g.adj[*i].push_back(v); } } return g; } void Graph::addEdge(int v, int w) { // Add w to v’s list. adj[v].push_back(w); } // The main function that returns true if graph // is strongly connected bool Graph::isSC() { // St1p 1: Mark all the vertices as not visited // (For first DFS) bool visited[V]; for (int i = 0; i < V; i++) visited[i] = false; // Step 2: Do DFS traversal starting from first vertex. DFSUtil(0, visited); // If DFS traversal doesn’t visit all vertices, // then return false. for (int i = 0; i < V; i++) if (visited[i] == false) return false; // Step 3: Create a reversed graph Graph gr = getTranspose(); // Step 4: Mark all the vertices as not visited // (For second DFS) for (int i = 0; i < V; i++) visited[i] = false; // Step 5: Do DFS for reversed graph starting from // first vertex. Starting Vertex must be same starting // point of first DFS gr.DFSUtil(0, visited); // If all vertices are not visited in second DFS, then // return false for (int i = 0; i < V; i++) if (visited[i] == false) return false; return true; } int main() { // Create graphs given in the above diagrams Graph g1(5); g1.addEdge(0, 1); g1.addEdge(1, 2); g1.addEdge(2, 3); g1.addEdge(3, 0); g1.addEdge(2, 4); g1.addEdge(4, 2); g1.isSC() ? cout << "Yes\n" : cout << "No\n"; Graph g2(4); g2.addEdge(0, 1); g2.addEdge(1, 2); g2.addEdge(2, 3); g2.isSC() ? cout << "Yes\n" : cout << "No\n"; return 0; }
Time Complexity: O(V + E), where V is the number of vertices and E is the number of edges. Each vertex and edge is processed exactly once in both DFS traversals.
Auxiliary Space: O(V) for storing the visited array and stack.
Note: The above approach requires two traversals of graph. We can find whether a graph is strongly connected or not in one traversal using Tarjan’s Algorithm to find Strongly Connected Components.
Explore
C++ Basics
Core Concepts
OOP in C++
Standard Template Library(STL)
Practice & Problems
My Profile