HDU - 确定比赛名次
#include<iostream>
#include<vector>
using namespace std;
const int maxn = 500+10;
vector<int>map[maxn];
int save[maxn];
int index[maxn];
bool used[maxn];
int n, m;
int flag;
//初始化
void init()
{
for(int i=0; i<=n; i++)
{
map[i].clear();
}
memset(used, false, sizeof(used));
memset(index, 0, sizeof(index));
}
//输入
void Input()
{
int a, b;
for(int i=1; i<=m; i++) //注意是m条边的输入
{
scanf("%d%d", &a, &b);
map[a].push_back(b);
index[b] ++; //入读加一
}
}
//查找入度为0的点
int find_zero()
{
for(int i=1; i<=n; i++)
{
if(!used[i] && index[i]==0)
return i;
}
return -1; //存在环
}
//剪掉所以先驱为k的点的边
void cut(int k)
{
for(int i=1; i<=map[k].size(); i++)
{
index[map[k][i-1]]--;
}
map[k].clear();
}
//执行拓扑排序
void topology()
{
int k;
for(int i=1; i<=n; i++)
{
k = find_zero();
if(k != -1)
{
cut(k);
used[k] = true;
save[i] = k;
}
else
flag = 0;//存在环
}
}
int main()
{
while(cin>>n>>m) //n个点 m条边
{
init();
Input();
flag = 1;
topology();
if(flag) //无环
for(int i=1; i<=n; i++)
{
printf((i==n)?"%d\n":"%d ", save[i]);
}
else
return -1;
}
return 0;
}