确定比赛名次

Time Limit : 2000/1000ms (Java/Other)   Memory Limit : 65536/32768K (Java/Other)
Total Submission(s) : 16   Accepted Submission(s) : 9
Problem Description
有N个比赛队(1<=N<=500),编号依次为1,2,3,。。。。,N进行比赛,比赛结束后,裁判委员会要将所有参赛队伍从前往后依次排名,但现在裁判委员会不能直接获得每个队的比赛成绩,只知道每场比赛的结果,即P1赢P2,用P1,P2表示,排名时P1在P2之前。现在请你编程序确定排名。
 
Input
输入有若干组,每组中的第一行为二个数N(1<=N<=500),M;其中N表示队伍的个数,M表示接着有M行的输入数据。接下来的M行数据中,每行也有两个整数P1,P2表示即P1队赢了P2队。
 

逃生

Time Limit : 2000/1000ms (Java/Other)   Memory Limit : 32768/32768K (Java/Other)
Total Submission(s) : 20   Accepted Submission(s) : 9
Problem Description
糟糕的事情发生啦,现在大家都忙着逃命。但是逃命的通道很窄,大家只能排成一行。

现在有n个人,从1标号到n。同时有一些奇怪的约束条件,每个都形如:a必须在b之前。
同时,社会是不平等的,这些人有的穷有的富。1号最富,2号第二富,以此类推。有钱人就贿赂负责人,所以他们有一些好处。

负责人现在可以安排大家排队的顺序,由于收了好处,所以他要让1号尽量靠前,如果此时还有多种情况,就再让2号尽量靠前,如果还有多种情况,就让3号尽量靠前,以此类推。

那么你就要安排大家的顺序。我们保证一定有解。

 
Input
第一行一个整数T(1 <= T <= 5),表示测试数据的个数。 然后对于每个测试数据,第一行有两个整数n(1 <= n <= 30000)和m(1 <= m <= 100000),分别表示人数和约束的个数。 然后m行,每行两个整数a和b,表示有一个约束a号必须在b号之前。a和b必然不同。
 
Output
对每个测试数据,输出一行排队的顺序,用空格隔开。
 
Sample Input
1
5 10
3 5
1 4
2 5
1 2
3 4
1 4
2 3
1 5
3 5
1 2
 
Sample Output
1 2 3 4 5
 
 

Output
给出一个符合要求的排名。输出时队伍号之间有空格,最后一名后面没有空格。 其他说明:符合条件的排名可能不是唯一的,此时要求输出时编号小的队伍在前;输入数据保证是正确的,即输入数据确保一定能有一个符合要求的排名。
 
Sample Input
4 3
1 2
2 3
4 3
 
Sample Output
1 2 4 3
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
题解
两者看着并没什么大的区别。
但前者是用最普通的拓扑排序,而后者需要反着来。
 
对普通的拓扑排序,由于题目需要按序,所以使用优先队列即可,将没有 前点 (即入度)的点入列,用这几个点的路径减少其他点的入度,然后将入度为0的入队,就行了。
 
而对于第二题,则由于要求的不同(先考虑1在尽量前,再考虑2尽量前。。。),我们将后点设为入度,同样的方法排序,反向输出即可。
 
可能有人会觉得两者差不多。
这里给个例子。
 
5 2(n,m)
5 1 
4 2

正向给出的答案是3 4 2 5 1 
反向给出的答案是1 2 3 4 5 
 
理解一下
 
以下是代码:
1285 确定比赛名次:
#include<bits/stdc++.h>
#define INF 0x3f3f3f3f
#define me(a,b) memset(a,b,sizeof(a))
#define N 5100
typedef long long ll;
using namespace std; int in[N],head[N],n,m,cnt,s,e;
priority_queue<int,vector<int>,greater<int> > q;
vector<int> ans; struct co
{
int e,pre;
}mp[N]; void init()
{
me(head,-);
cnt=;
me(in,);
while(!q.empty())
q.pop();
ans.clear();
} void add(int ss,int ee)
{
mp[cnt].e=ee;
mp[cnt].pre=head[ss];
head[ss]=cnt++;
} int main()
{
//freopen("in.txt","r",stdin);
while(~scanf("%d%d",&n,&m))
{
init();
while(m--)
{
scanf("%d%d",&s,&e);
in[e]++;
add(s,e);
}
for(int i=;i<=n;i++)
{
if(in[i]==)
{
q.push(i);
}
}
while(!q.empty())
{
int f=q.top();
ans.push_back(f);
q.pop();
for(int i=head[f]; i!=-; i=mp[i].pre)
{
in[mp[i].e]--;
if(in[mp[i].e]==)
{
q.push(mp[i].e);
}
} }
for(int i=;i<ans.size();i++)
{
if(i)
cout<<' ';
cout<<ans[i];
}
cout<<endl;
}
}

4857:

#include<bits/stdc++.h>
#define INF 0x3f3f3f3f
#define me(a,b) memset(a,b,sizeof(a))
#define N 100010
typedef long long ll;
using namespace std; int in[],head[N],n,m,cnt,s,e;
priority_queue<int> q;
vector<int> ans; struct co
{
int e,pre;
}mp[N]; void init()
{
me(head,-);
me(in,);
cnt=;
while(!q.empty())
q.pop();
ans.clear();
} void add(int ss,int ee)
{
mp[cnt].e=ee;
mp[cnt].pre=head[ss];
head[ss]=cnt++;
} int main()
{
//freopen("in.txt","r",stdin);
int T;
cin>>T;
while(T--)
{
init();
scanf("%d%d",&n,&m);
while(m--)
{
scanf("%d%d",&s,&e);
in[s]++;
add(e,s);
}
for(int i=;i<=n;i++)
{
if(in[i]==)
{
q.push(i);
}
}
while(!q.empty())
{
int f=q.top();
ans.push_back(f);
q.pop();
for(int i=head[f]; i!=-; i=mp[i].pre)
{
in[mp[i].e]--;
if(in[mp[i].e]==)
{
q.push(mp[i].e);
}
} }
for(int i=ans.size()-;i>-;i--)
{
cout<<ans[i];
if(i)
cout<<' ';
}
cout<<endl;
}
}
 

正向与反向拓扑排序的区别(hdu 1285 确定比赛名次和hdu 4857 逃生)的更多相关文章

  1. ACM: HDU 1285 确定比赛名次 - 拓扑排序

     HDU 1285 确定比赛名次 Time Limit:1000MS     Memory Limit:32768KB     64bit IO Format:%I64d & %I64u De ...

  2. HDU.1285 确定比赛名次 (拓扑排序 TopSort)

    HDU.1285 确定比赛名次 (拓扑排序 TopSort) 题意分析 裸的拓扑排序 详解请移步 算法学习 拓扑排序(TopSort) 只不过这道的额外要求是,输出字典序最小的那组解.那么解决方案就是 ...

  3. hdu 1285 确定比赛名次 拓扑排序

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1285 有N个比赛队(1<=N<=500),编号依次为1,2,3,....,N进行比赛,比赛 ...

  4. HDU 1285 确定比赛名次(拓扑排序模板)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1285 题目大意:有N个比赛队(1<=N<=500),编号依次为1,2,3,....,N进行 ...

  5. HDU 1285 确定比赛名次(拓扑排序)题解

    Problem Description 有N个比赛队(1<=N<=500),编号依次为1,2,3,....,N进行比赛,比赛结束后,裁判委员会要将所有参赛队伍从前往后依次排名,但现在裁判委 ...

  6. [ACM] hdu 1285 确定比赛名次 (拓扑排序)

    确定比赛名次 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Subm ...

  7. hdu 1285 确定比赛名次 (拓扑)

    确定比赛名次 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Subm ...

  8. HDU 1285 确定比赛名次

    传送门 确定比赛名次 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total ...

  9. 题解报告:hdu 1285 确定比赛名次

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1285 Problem Description 有N个比赛队(1<=N<=500),编号依次 ...

随机推荐

  1. dll导出函数的两种方式的比较

    最初的网页链接已经挂了, 在此贴一个中间的转载链接 https://blog.csdn.net/zhazhiqiang/article/details/51577523 一 概要 vs中导出 dll的 ...

  2. 01-使用eclipse新建一个标准的 java web项目

    1.使用eclipse创建个普通的Java SE项目  名称:CRM java web标准目录结构 crm WEB-INF classes lib web.xml 设置项目字节码输出目录

  3. Scaffold-DbContext 命令参数

    NAME Scaffold-DbContext SYNOPSIS Scaffolds a DbContext and entity types for a database. SYNTAX Scaff ...

  4. 关于mpi的理论知识以及编写程序来实现数据积分中的梯形积分法。

    几乎所有人的第一个程序是从“hello,world”程序开始学习的 #include "mpi.h" #include <stdio.h> int main(int a ...

  5. NOIP 2018 Day1

    Fei2Xue@Lian$Tian! 三道原题qwq真的凉 半年前看到有人发说说,梦见省选打开题目,是Please contact lydsy2012@163.com! 没想到一语成谶 大众分300 ...

  6. thunderbird 日历

    参考: Configuring Thunderbird and Using it to Access Office 365 Mail and Calendar in Cardiff Universit ...

  7. java异常——Exception、RuntimException

    一.Exception和RuntimeException的区别 Exception是RuntimeException的父类,使用了 Exception 的类都必须对异常进行处理(try / throw ...

  8. python大法好——python json

    Python JSON 本章节我们将为大家介绍如何使用 Python 语言来编码和解码 JSON 对象. JSON(JavaScript Object Notation) 是一种轻量级的数据交换格式, ...

  9. part1

    一.hello world 明确的指出 hello.py 脚本由 python 解释器来执行.coding:utf-8处理脚本中的中文 #!/usr/bin/env python # _*_ codi ...

  10. 远程git仓库的搭建

    具体的操作见另一篇 第一部分: 安装 1. 下载地址:  https://git-scm.com/download/win; 如果速度慢, 使用 迅雷下载; 2. 点击安装, 然后下一步, 直到下面这 ...