受欢迎的牛
Description
每一头牛的愿望就是变成一头最受欢迎的牛。现在有N头牛,给你M对整数(A,B),表示牛A认为牛B受欢迎。这种关系是具有传递性的,如果A认为B受欢迎,B认为C受欢迎,那么牛A也认为牛C受欢迎。你的任务是求出有多少头牛被所有的牛认为是受欢迎的。
Input
第一行两个数N,M。
接下来M行,每行两个数A,B,意思是A认为B是受欢迎的(给出的信息有可能重复,即有可能出现多个A,B)
Output
一个数,即有多少头牛被所有的牛认为是受欢迎的。
Sample Input
3 3 1 2 2 1 2 3
Sample Output
1
代码
#include<iostream>
using namespace std;
struct point{
int to,next;
};
point a[100005];
int cnt=0,h[10005];
void add(int x,int y){
a[++cnt].to=y;
a[cnt].next=h[x];
h[x]=cnt;
}
int L[10005],D[10005],sign=0,stack_[10005],stackn=0;
int scc[10005],ssc=0,s[10005];
void tarjan(int u){
L[u]=D[u]=++sign;
stack_[++stackn]=u;
for(int i=h[u];i;i=a[i].next){
if(D[a[i].to]==0){
tarjan(a[i].to);
L[u]=min(L[u],L[a[i].to]);
}
else if(scc[a[i].to]==0)L[u]=min(L[u],D[a[i].to]);
}
if(L[u]==D[u]){
ssc++;
int ss=0;
while(stack_[stackn]!=u){
scc[stack_[stackn]]=ssc;
stackn--;
ss++;
}
scc[stack_[stackn]]=ssc;
stackn--;
s[ssc]=ss+1;
}
}
int bj[10005];
int main(){
int n,m,x,y;
cin>>n>>m;
for(int i=1;i<=m;i++){
cin>>x>>y;
add(x,y);
}
for(int i=1;i<=n;i++)if(D[i]==0)tarjan(i);
for(int i=1;i<=n;i++)
for(int j=h[i];j;j=a[j].next){
if(scc[i]==scc[a[j].to])continue;
bj[scc[i]]=1;
}
int ans=0;
for(int i=1;i<=n;i++){
if(bj[scc[i]]==0){
if(ans!=0){
cout<<0<<endl;
return 0;
}
ans=s[scc[i]];
bj[scc[i]]=1;
}
}
cout<<ans<<endl;
return 0;
}