代码:
#include<iostream> #include<cstdio> #include<cmath> #include<map> #include<queue> #include<vector> #include<cstring> #include<algorithm> #define rep(i,a,b) for(int i=(a);i<(b);i++) #define rev(i,a,b) for(int i=(a);i>=(b);i--) #define clr(a,x) memset(a,x,sizeof a) #define INF 0x3f3f3f3f typedef long long LL; using namespace std; const int maxn=105; const int maxm=maxn*maxn; int first[maxn],ecnt,v[maxm],nex[maxm]; int low[maxn],dfn[maxn],stck[maxn],belong[maxn]; int index,top,scc; bool ins[maxn]; int num[maxn]; int in[maxn],out[maxn]; int n,m; void tarjan(int u) { low[u]=dfn[u]=++index; stck[top++]=u; ins[u]=1; for(int e=first[u];~e;e=nex[e]) { if(!dfn[v[e]]) { tarjan(v[e]); low[u]=min(low[u],low[v[e]]); } else if(ins[v[e]])low[u]=min(low[u],dfn[v[e]]); } if(low[u]==dfn[u]) { int v; scc++; do { v=stck[--top]; ins[v]=false; belong[v]=scc; num[scc]++; }while(v!=u); } } void solve(int n) { clr(dfn,0); clr(ins,0); clr(num,0); index=scc=top=0; for(int i=1;i<=n;i++) if(!dfn[i])tarjan(i); } void add_(int a,int b) { v[ecnt]=b; nex[ecnt]=first[a]; first[a]=ecnt++; } void init() { ecnt=0; clr(first,-1); } int main() { while(~scanf("%d",&n)) { init(); int ans1=0,ans2=0; for(int i=1;i<=n;i++) { while(~scanf("%d",&m)&&m) add_(i,m); } solve(n); clr(out,0); clr(in,0); for(int i=1;i<=n;i++) for(int j=first[i];~j;j=nex[j]) if(belong[i]!=belong[v[j]]) { out[belong[i]]++; in[belong[v[j]]]++; } for(int i=1;i<=scc;i++) { if(in[i]==0)ans1++; if(out[i]==0)ans2++; } if(scc==1)printf("1\n0\n"); else printf("%d\n%d\n",ans1,max(ans1,ans2)); } return 0; }
时间: 2024-10-12 12:48:27