(广东工业大学ACM寒假集训专题三K)
Cow Contest
Time Limit: 1000MS Memory Limit: 65536K
Total Submissions: 24291 Accepted: 13514
Description
N (1 ≤ N ≤ 100) cows, conveniently numbered 1…N, are participating in a programming contest. As we all know, some cows code better than others. Each cow has a certain constant skill rating that is unique among the competitors.
The contest is conducted in several head-to-head rounds, each between two cows. If cow A has a greater skill level than cow B (1 ≤ A ≤ N; 1 ≤ B ≤ N; A ≠ B), then cow A will always beat cow B.
Farmer John is trying to rank the cows by skill level. Given a list the results of M (1 ≤ M ≤ 4,500) two-cow rounds, determine the number of cows whose ranks can be precisely determined from the results. It is guaranteed that the results of the rounds will not be contradictory.
Input
- Line 1: Two space-separated integers: N and M
- Lines 2…M+1: Each line contains two space-separated integers that describe the competitors and results (the first integer, A, is the winner) of a single round of competition: A and B
Output
- Line 1: A single integer representing the number of cows whose ranks can be determined
Sample Input
5 5
4 3
4 2
3 2
1 2
2 5
Sample Output
2
乍一看看不出来是Floyd算法,但是你试一下把图画出来,箭头表示胜负关系,然后就会发现,5号一定是最后一位,因为1,4,3都能打败2,2能打败5,所以5没有人能打败,同时呢2也可以确定了。所以,其实是只要能确定某个点(牛)和所有点(牛)的胜负关系,那么就那确定他的位置。
也就是判断图某点的入度和出度加起来是否等于总牛数减一(去掉他自己)。
#include<iostream>//FLYOD
#include<cstring>
using namespace std;
//const int inf=0x3f3f3f;
int mp[110][110];
int main()
{
int n,m;
scanf("%d %d",&n,&m);
memset(mp,0,sizeof(mp));
for(int i=1;i<=n;i++)mp[i][i]=1;//对角设1,算作自己到自己连通(0也可以)
int a,b;
for(int i=1;i<=m;i++){
scanf("%d %d",&a,&b);//a->b
mp[a][b]=1;//1代表有路()
}
for(int k=1;k<=n;k++)//Floyd
for(int i=1;i<=n;i++)
for(int j=1;j<=n;j++){
if(mp[i][k]&&mp[k][j]){
mp[i][j]=1;//只要有路,就设1
}
}
int ans=0;
for(int i=1;i<=n;i++){
int ins=0;//计算出入度
for(int j=1;j<=n;j++){
ins+=mp[i][j];//遍历矩阵,需要遍历第i行和第i列
if(i==j)continue;//不重复加(初始化对角为0可以不判断)
ins+=mp[j][i];
}
if(ins==n)ans++;//如果初始化对角为0,这里就是n-1
}
printf("%d\n",ans);
}