bzoj1051(明星奶牛)
这道就是明星奶牛,A了一次又一次了,(⊙o⊙)…(⊙o⊙)…
去年pas就打了不下5次,就是强联通缩点,然后求出度为0的块
判断有多个的话就无解,一个就输出块的大小。
1 #include<cstdio> 2 #include<iostream> 3 #include<algorithm> 4 #include<cmath> 5 #include<cstring> 6 using namespace std; 7 8 const int NN=1e4+7,MM=NN*5; 9 10 int n,m,Time=0,top=0,scc=0,ans; 11 int dfn[NN],low[NN],instack[NN],q[NN],belong[NN],chu[NN]; 12 int cnt=0,head[NN],next[MM],rea[MM],skt[NN]; 13 14 void add(int u,int v) 15 { 16 cnt++; 17 next[cnt]=head[u]; 18 head[u]=cnt; 19 rea[cnt]=v; 20 } 21 void tarjan(int u) 22 { 23 low[u]=dfn[u]=++Time; 24 q[++top]=u,instack[u]=1; 25 for (int i=head[u];i!=-1;i=next[i]) 26 { 27 int v=rea[i]; 28 if (dfn[v]==0) 29 { 30 tarjan(v); 31 low[u]=min(low[v],low[u]); 32 } 33 else if (instack[v]) low[u]=min(low[u],dfn[v]); 34 } 35 if (low[u]==dfn[u]) 36 { 37 scc++; 38 int x=-1; 39 while (x!=u) 40 { 41 x=q[top--]; 42 instack[x]=0; 43 belong[x]=scc; 44 ++skt[scc]; 45 } 46 } 47 } 48 void rebuild() 49 { 50 for (int u=1;u<=n;u++) 51 { 52 for (int i=head[u];i!=-1;i=next[i]) 53 { 54 int v=rea[i]; 55 if (belong[u]!=belong[v]) chu[belong[u]]=1; 56 } 57 } 58 int num=0,x=0; 59 for (int i=1;i<=scc;i++) 60 if (chu[i]==0) num++,x=i; 61 if (num!=1) ans=0; 62 else ans=skt[x]; 63 printf("%d",ans); 64 } 65 int main() 66 { 67 scanf("%d%d",&n,&m); 68 int x,y; 69 memset(head,-1,sizeof(head)); 70 for (int i=1;i<=m;i++) 71 { 72 scanf("%d%d",&x,&y); 73 add(x,y); 74 } 75 for (int i=1;i<=n;i++) 76 if (dfn[i]==0) tarjan(i); 77 rebuild(); 78 }