SCC (Edge Flip Trick)
Finding the Strongly Connected Component (SCC) of a given vertex using the edge flip trick. Instead of checking each candidate separately (naive), we reverse all edges and run just 2 DFS searches! Complexity: O(V+E) instead of O(VΓ(V+E)).
- β’Finding the strongly connected component of a given vertex in a directed graph
- β’Foundation for Kosaraju's and Tarjan's algorithms
Time
O(V+E)
Memory
O(V+E)
V = number of vertices
E = number of edges
Read the story related to this algorithm to better understand when and why it is used. You can also maximize the story window to fully immerse yourself in it.
Operation Snowball
Winter has arrived in your village. Snow covers every rooftop, every fence, every tree branch. You look out the window and think: "It's time for the ultimate snow battle."
The edge flip trick is a clever way to find the Strongly Connected Component (SCC) of a given vertex in O(V+E) time β much faster than the naive O(VΓ(V+E)) approach!
The idea is simple:
- Forward DFS from our vertex β checking who we can reach
- Reverse all edges in the graph (every arrow changes direction)
- DFS on the reversed graph from the same vertex β every vertex found is someone who could reach us on the original graph!
- Intersection of both sets = our SCC
Why does this work? If someone can reach us via path A β B β C β Our House, then after reversing edges that path becomes Our House β C β B β A. We can walk it with DFS from our house! And conversely β if someone can NOT reach us, there's no path to reverse, so DFS on the reversed graph won't find them either.
A Strongly Connected Component (SCC) of vertex v is the largest set of vertices S containing v, such that for every pair of vertices a, b in S there exists a path from a to b AND from b to a.
In other words: in an SCC, everyone can reach everyone.
Key observation β the "hub" trick: If we pick one vertex as a "hub" (e.g., our house), we only need to check:
- Who can the hub reach? (forward DFS)
- Who can reach the hub? (DFS on reversed graph)
The intersection of these two sets gives us the hub's SCC! Why? Because if Bartek can reach our house, and from our house we can reach Dominik, then Bartek can reach Dominik β through our house.
Example: Graph with 5 vertices:
- 0β1, 1β2, 2β0, 2β3, 3β4
- From vertex 0 we can reach: {0, 1, 2, 3, 4}
- Who can reach 0 (DFS on reversed): {0, 1, 2}
- SCC(0) = {0, 1, 2} β© {0, 1, 2, 3, 4} = {0, 1, 2}
- Vertices 3 and 4 are NOT in SCC(0), because they can't reach 0.
Vertices 0, 1, 2 (green) form an SCC β everyone can reach everyone. Vertices 3 and 4 are outside the SCC because they can't reach 0.
Instead of asking each candidate separately "Can you reach me?", we use a clever trick:
Reverse ALL edges in the graph β every arrow changes to the opposite direction.
Why does this help? Because if someone can reach us via path:
Bartek β Kasia β Our House
Then after reversing edges, that path becomes:
Our House β Kasia β Bartek
Now we can walk that path with DFS from our house! One DFS on the reversed graph replaces many separate DFS searches.
Formally:
- If a path A β B exists in the original graph, then after reversing a path B β A exists
- If NO path A β B exists, then after reversing NO path B β A exists
This means the set of vertices reachable from our house on the reversed graph is EXACTLY the same set as vertices that can reach us on the original graph!
Input: Directed graph and a starting vertex (our house).
Step 1: Reverse edges Create a reversed graph β for each edge uβv add vβu.
Step 2: Forward DFS
Run DFS from our house on the original graph. Save the set who_i_can_reach.
Step 3: DFS on reversed graph
Run DFS from our house on the reversed graph. Save the set who_can_reach_me.
Step 4: Intersection
SCC = who_i_can_reach β© who_can_reach_me
Example on graph {0:[1], 1:[2], 2:[0,3], 3:[4], 4:[]}:
| Step | Set |
|---|---|
| Forward DFS from 0 | {0, 1, 2, 3, 4} |
| Reversed graph | {0:[2], 1:[0], 2:[1], 3:[2], 4:[3]} |
| Reversed DFS from 0 | {0, 2, 1} |
| SCC = intersection | {0, 1, 2} |
Complexity: O(V+E) β two DFS searches + one edge reversal!
We need to prove two things:
Part 1: If someone CAN reach us β DFS on reversed graph WILL find them
Proof: Let there be a path vβ β vβ β ... β vβ β our_house on the original graph. After reversing edges, this path becomes our_house β vβ β ... β vβ β vβ. DFS from our house on the reversed graph can walk this path and find vβ. β
Part 2: If someone CANNOT reach us β DFS on reversed graph will NOT find them
Proof by contradiction: Assume there is NO path Ewa β our_house on the original graph, but DFS on the reversed graph DOES find Ewa. This means a path our_house β ... β Ewa exists on the reversed graph. But every path on the reversed graph corresponds to a reversed path on the original graph. So Ewa β ... β our_house must exist on the original graph β CONTRADICTION with our assumption! β
Conclusion: The set of vertices found by DFS on the reversed graph = exactly the set of vertices that can reach our house. No false positives, no false negatives.
| Naive SCC | Edge Flip Trick | |
|---|---|---|
| Question "who can reach me?" | DFS for each candidate separately | One DFS on reversed graph |
| Number of DFS searches | 1 + V (forward + for each candidate) | 2 (forward + on reversed) |
| Time complexity | O(V Γ (V+E)) | O(V+E) |
| Space complexity | O(V+E) | O(V+E) |
| Extra cost | None | Reversing graph: O(V+E) |
The flip trick is much faster β we run only 2 DFS searches instead of V+1!
Note: This algorithm finds the SCC of only ONE vertex. To find ALL SCCs in a graph, we use Kosaraju's or Tarjan's algorithm β but that's a topic for another lesson!
Tip: To better understand how the Python code works, go to the Interactive Debugger tab at the top of the page. You will see the code executed step by step with a visualization of the graph and call stack.
Below you'll find code for finding the strongly connected component from a given vertex using the edge flip trick. Click on code lines to see detailed explanation.
Click on a code line to see the explanation