Sorting It All Out
Time Limit: 1000MS | Memory Limit: 10000K | |
Total Submissions: 37849 | Accepted: 13361 |
Description
An ascending sorted sequence of distinct values is one in which some form of a less-than operator is used to order the elements from smallest to largest. For example, the sorted sequence A, B, C, D implies that A < B, B < C and C < D. in this problem, we will give you a set of relations of the form A < B and ask you to determine whether a sorted order has been specified or not.
Input
Input consists of multiple problem instances. Each instance starts with a line containing two positive integers n and m. the first value indicated the number of objects to sort, where 2 <= n <= 26. The objects to be sorted will be the first n characters of the uppercase alphabet. The second value m indicates the number of relations of the form A < B which will be given in this problem instance. Next will be m lines, each containing one such relation consisting of three characters: an uppercase letter, the character "<" and a second uppercase letter. No letter will be outside the range of the first n letters of the alphabet. Values of n = m = 0 indicate end of input.
Output
For each problem instance, output consists of one line. This line should be one of the following three:
Sorted sequence determined after xxx relations: yyy...y.
Sorted sequence cannot be determined.
Inconsistency found after xxx relations.
where xxx is the number of relations processed at the time either a sorted sequence is determined or an inconsistency is found, whichever comes first, and yyy...y is the sorted, ascending sequence.
Sorted sequence determined after xxx relations: yyy...y.
Sorted sequence cannot be determined.
Inconsistency found after xxx relations.
where xxx is the number of relations processed at the time either a sorted sequence is determined or an inconsistency is found, whichever comes first, and yyy...y is the sorted, ascending sequence.
Sample Input
4 6 A<B A<C B<C C<D B<D A<B 3 2 A<B B<A 26 1 A<Z 0 0
Sample Output
Sorted sequence determined after 4 relations: ABCD. Inconsistency found after 2 relations. Sorted sequence cannot be determined.
Source
题目大意:对字母表前n个字母,给出你它们m个关系,在这m个关系中,看看是否能确定它们的严格拓扑序,就是大小关系是唯一的(每一个字母只能有一个排在它们前面或者后面),如果不唯一就输出“Sorted sequence cannot be determined.”,如果前k个关系中发现有环,就输出“Inconsistency found after k relations.”,前k个关系能确定严格的排序关系就输出Sorted sequence determined after k relations: 排列顺序.所以说对于每次输入的关系你都要进行拓扑排序一次。
首先我们来讲一下什么是拓扑序,就是按照关系排序,和现实生活中的祖先后代那样的关系类似,
严格排序就是:
你只能有一个爸爸和儿子,
没有环就是:
你爸爸不能是你儿子,你爸爸不能是你儿子的儿子这样的关系。
那么我们怎样来求这个关系呢?方法就是:
每次找到入度为0的那个结点加入队列,然后删除它,并且把它所指向的节点的入度减一,在进行此类操作,如果操作数等于总结点数,那么这个关系就是正确的。
那么在这道题中,我们还要求严格排序,所以每次入队的节点数只能是1
AC代码:
#include<stdio.h>
#include<iostream>
#include<algorithm>
#include<string.h>
#include<math.h>
#include<stdlib.h>
#include<queue>
#include<map>
#include<set>
#define bug printf("*********\n");
#define mem0(a) memset(a, 0, sizeof(a));
#define mem1(a) memset(a, -1, sizeof(a));
#define in1(a) scanf("%d" ,&a);
#define in2(a, b) scanf("%d%d", &a, &b);
#define out1(a) printf("%d\n", a);
#define out2(a, b) printf("%d %d\n", a, b);
using namespace std;
typedef long long LL;
typedef pair<int, int> par;
const int mod = 1e9+7;
const int INF = 1e9+7;
const int N = 1000010;
const double pi = 3.1415926;
int n, m, cnt, s, flag, ok, idx;
int head[30], d[30], du[30], put[30];
char str[10];
void inti()
{
mem0(d);
mem1(head);
cnt = 0;
flag = 0;
s = 0;
ok = 0;
}
struct edge //我们用邻接表来存关系,也可以用邻接矩阵
{
int end;
int next;
}e[10010];
void add(int u, int v)
{
e[cnt].end = v;
e[cnt].next = head[u];
head[u] = cnt ++;
}
int topo()
{
queue<int> q;
while(!q.empty()) q.pop();
memcpy(du, d, sizeof(d)); //更新关系
//注意下:用这个函数一定要注意空间的大小,否则会修改你其他数组的值
for(int i = 0; i < n; i ++) {
if(du[i] == 0)
q.push(i);
}
s = 0;
int f = 1;
while(!q.empty()) {
if(q.size() > 1) f = 0;
int cur;
cur = q.front();
q.pop();
put[s ++] = cur;
for(int i = head[cur]; i != -1; i = e[i].next) {
int en = e[i].end;
du[en] --;
if(du[en] == 0)
q.push(en);
}
}
if(s != n) return -1;
return f;
}
int main()
{
int x, y;
while(~scanf("%d%d", &n, &m) && n && m) {
inti();
for(int i = 0; i < m; i ++) {
scanf("%s", str);
x = str[2] - 'A';
y = str[0] - 'A';
add(x, y);
d[y] ++;
if(flag == 1 || flag == -1) continue;
//如果已经确定顺序或者发现有环就不用再继续排序了
flag = topo();
if(flag == -1) ok = 1;
idx = i+1; //位置记录
}
if(flag == 1) {
printf("Sorted sequence determined after %d relations: ", idx);
for(int i = s-1; i >= 0; i --)
printf("%c", put[i]+'A');
printf(".\n");
}else if(ok) printf("Inconsistency found after %d relations.\n", idx);
else printf("Sorted sequence cannot be determined.\n");
}
return 0;
}