poj 2762 Going from u to v or from v to u?(强连通、缩点、拓扑)
题意:(理解错了)在一个洞穴中有多个room,要求任意选两个room:u、v,都能保证u、v之间有通路,注意洞穴中的路是有向边。、
分析:强连通子图中的点必然两两之间可以互通,两个强连通子图之间有通路,必须在树上构成父子关系(不一定相邻),又两两之间有通路,即任意两个点u、v都存在父子关系——所有强连通子图构成一条链。
错误:tarjin初始化忘记更新scc_cnt=dfs_clock=0;
1 #include<cstdio> 2 #include<cstring> 3 #include<queue> 4 #include<stack> 5 #include<vector> 6 #include<algorithm> 7 using namespace std; 8 9 const int MAXN=1111; 10 11 struct Edge{ 12 int v,next; 13 Edge(){} 14 Edge(int _v,int _next):v(_v),next(_next){} 15 }edge[MAXN*10]; 16 17 struct Tp{ 18 int u,c; 19 Tp(){} 20 Tp(int _u,int _c):u(_u),c(_c){} 21 }; 22 23 int pre[MAXN],low[MAXN],sccno[MAXN],scc_cnt,dfs_clock; 24 int head[MAXN],tol; 25 stack<int>stk; 26 27 //int mp[MAXN][MAXN];//去重边反而跑的时间更长 28 vector<int>G[MAXN]; 29 30 int in[MAXN],color[MAXN]; 31 queue<Tp>q; 32 33 void init() 34 { 35 tol=0; 36 memset(head,-1,sizeof(head)); 37 } 38 39 void add(int u,int v) 40 { 41 edge[tol]=Edge(v,head[u]); 42 head[u]=tol++; 43 } 44 45 void dfs(int u) 46 { 47 int v; 48 pre[u]=low[u]=++dfs_clock; 49 stk.push(u); 50 for(int i=head[u];i!=-1;i=edge[i].next) 51 { 52 v=edge[i].v; 53 if(!pre[v]){ 54 dfs(v); 55 low[u]=min(low[u],low[v]); 56 }else if(!sccno[v]) 57 low[u]=min(low[u],pre[v]); 58 } 59 if(pre[u]==low[u]){ 60 scc_cnt++; 61 do{ 62 v=stk.top(); 63 stk.pop(); 64 sccno[v]=scc_cnt; 65 }while(u!=v); 66 } 67 } 68 69 void find_scc(int n) 70 { 71 dfs_clock=scc_cnt=0; 72 memset(pre,0,sizeof(pre)); 73 memset(low,0,sizeof(low)); 74 memset(sccno,0,sizeof(sccno)); 75 76 for(int i=1;i<=n;i++) 77 if(!pre[i]) 78 dfs(i); 79 } 80 81 int main() 82 { 83 int T; 84 int n,m; 85 scanf("%d",&T); 86 while(T--) 87 { 88 scanf("%d%d",&n,&m); 89 90 init(); 91 for(int i=0;i<m;i++) 92 { 93 int u,v; 94 scanf("%d%d",&u,&v); 95 add(u,v); 96 } 97 98 find_scc(n); 99 100 memset(in,0,sizeof(in)); 101 for(int i=1;i<=scc_cnt;i++) 102 G[i].clear(); 103 //memset(mp,0,sizeof(mp)); 104 for(int i=1;i<=n;i++) 105 for(int j=head[i];j!=-1;j=edge[j].next) 106 if(sccno[i]!=sccno[edge[j].v]){ 107 //if(mp[sccno[i]][sccno[edge[j].v]]==0){ 108 G[sccno[i]].push_back(sccno[edge[j].v]); 109 //mp[sccno[i]][sccno[edge[j].v]]=1; 110 in[sccno[edge[j].v]]++; 111 //} 112 } 113 for(int i=1;i<=scc_cnt;i++) 114 if(!in[i]) 115 q.push(Tp(i,1)); 116 117 memset(color,0,sizeof(color)); 118 Tp e; 119 while(!q.empty()) 120 { 121 e=q.front();q.pop(); 122 color[e.c]++; 123 int sz=G[e.u].size(); 124 for(int i=0;i<sz;i++) 125 { 126 in[G[e.u][i]]--; 127 if(in[G[e.u][i]]==0){ 128 q.push(Tp(G[e.u][i],e.c+1)); 129 } 130 } 131 } 132 133 int flog=1; 134 for(int i=1;i<=e.c;i++) 135 if(color[i]>1){ 136 flog=0; 137 break; 138 } 139 140 if(!flog) 141 printf("No\n"); 142 else 143 printf("Yes\n"); 144 } 145 return 0; 146 }