Question:
Given a directed graph, the number of vertices is obtained from any vertex.
Number of vertices <= 10,000, number of edges <= 50,000
Theorem:
A point with a unique outbound degree of 0 in a directed acyclic graph can certainly be reached by any point.
(Because there is no ring, moving forward from any point must end at a point with an outbound degree of 0)
1. Find all strongly connected components
2. Each strongly connected component is reduced to a point to form a directed acyclic graph Dag.
3. If there is a unique point with an exit of 0 on the Dag, the point can be reached by all points. Then, all the points in the source image on the connected component represented by this point can be reached by all points in the source image. Then, the points of this connected component are the answer.
4. If there is more than one vertex with an outbound degree of 0 on the Dag, These vertices are inaccessible to each other. The original question is unsolved and the answer is 0.
#include <cstdio>#include <cstring>#include <vector>#include <stack>#include <iostream>#include <algorithm>using namespace std;const int maxn = 10000 + 100;vector<int> g[maxn];int dfn[maxn], low[maxn], belong[maxn], dfs_clock, scc_cnt, size[maxn];stack<int> s;int n, m;void dfs(int u){ dfn[u] = low[u] = ++dfs_clock; s.push(u); for(int i=0; i<g[u].size(); ++i){ int v = g[u][i]; if(!dfn[v]){ dfs(v); low[u] = min(low[u], low[v]); }else if(!belong[v]){ low[u] = min(low[u], dfn[v]); } } if(low[u] == dfn[u]){ scc_cnt++; for(;;){ int x = s.top(); s.pop(); belong[x] = scc_cnt; size[scc_cnt]++; if(x == u) break; } } } void find_scc(int n){ dfs_clock = scc_cnt = 0; memset(belong, 0, sizeof belong ); memset(dfn, 0, sizeof dfn ); for(int i=1; i<=n; ++i) if(!dfn[i]) dfs(i); } int main(){scanf("%d%d", &n, &m);int u, v;for(int i=0; i<m; ++i){scanf("%d%d", &u, &v);g[u].push_back(v);}find_scc(n);int out[maxn];memset(out, 0, sizeof out );for(int i=1; i<=n; ++i){for(int j=0; j<g[i].size(); ++j){int &v = g[i][j];if(belong[i] != belong[v]){out[belong[i]]++;}}}int cnt = 0, ans;for(int i=1; i<=scc_cnt; ++i){if(out[i]==0){cnt++;ans = size[i];}}if(cnt==1){printf("%d\n", ans);}else {printf("0\n");}return 0;}
Poj2186 popular cows, directed graph, and Tarjan Algorithm