poj 2186 (求一个图中可以到达所有点的点的个数) (强连通)

来源:互联网 发布:服务器端口检测 编辑:程序博客网 时间:2024/06/05 23:55
#include<cstdio>#include<cstring>#include<vector>#define MAX_N 10000+16using namespace std;vector<int>G[MAX_N];vector<int>rG[MAX_N];vector<int>vs;bool vis[MAX_N];int cmp[MAX_N];int n,m,V;void add_edge(int from,int to){G[from].push_back(to);rG[to].push_back(from);} void dfs(int v){   vis[v]=1;   for(int i=0;i<G[v].size();i++)   {   if(!vis[G[v][i]])   dfs(G[v][i]);   }   vs.push_back(v);}void rdfs(int v,int k){vis[v]=1;cmp[v]=k;for(int i=0;i<rG[v].size();i++){if(!vis[rG[v][i]])rdfs(rG[v][i],k);}}int scc(){memset(vis,0,sizeof(vis));vs.clear();for(int v=0;v<V;v++){if(!vis[v])dfs(v);}memset(vis,0,sizeof(vis));int k=0;for(int i=vs.size()-1;i>=0;i--){if(!vis[vs[i]])rdfs(vs[i],k++);} return k;}int main(){int a,b;scanf("%d%d",&n,&m);V=n;for(int i=0;i<m;i++){scanf("%d%d",&a,&b);add_edge(a-1,b-1);} int res=scc();int u=0,num=0;for(int v=0;v<V;v++){if(cmp[v]==res-1){u=v;num++;}}memset(vis,0,sizeof(vis));rdfs(u,0);for(int v=0;v<V;v++)    {    if(!vis[v])    {    num=0;    break;}}printf("%d\n",num);}

0 0
原创粉丝点击