// br = bridges, p = parent vector<pair<int, int>> br; int dfsBR(int u, int p) { low[u] = disc[u] = ++Time; for (int& v : adj[u]) { if (v == p) continue; // we don't want to go back through the same path. // if we go back is because we found another way back if (!disc[v]) { // if V has not been discovered before dfsBR(v, u); // recursive DFS call if (disc[u] < low[v]) // condition to find a bridge br.push_back({u, v}); low[u] = min(low[u], low[v]); // low[v] might be an ancestor of u } else // if v was already discovered means that we found an ancestor low[u] = min(low[u], disc[v]); // finds the ancestor with the least discovery time } } void BR() { low = disc = vector<int>(adj.size()); Time = 0; for (int u = 0; u < adj.size(); u++) if (!disc[u]) dfsBR(u, u) }