标签:
参考来源:joy_w
/*
*POJ 1094 Sorting It All Out
*参考http://hi.baidu.com/bnjyjncwbdbjnzr/item/a4ffa006defc47c42f4c6bd5
*以邻接表为图的存储结构的算法:
*a)扫描顶点表,将入度为零的顶点入栈;
(ps:这里栈可以使优先队列 and so on)
*b)当栈非空时:
* 输出栈顶元素v:出栈;
* 检查v的出边,将每条出边的终端顶点的入度减1,若该顶点入度为0,入栈;
*c)当栈空时,若输出的顶点小于顶点数,则说明AOV网有回路,否则拓扑排序完成.
*/
/*
本题:
首先是用邻接表存储 各个点的先后顺序;
再用cnt[]数组存储每个点的入度;
每输入一条边就需判断一下,是否是矛盾(产生环),还是顺序已经确定;
如果输入完后,仍然不能判断就是"Sorted sequence cannot be determined."
*/
#include <cstdio>
#include <cstring>
#define MAXN 29
int n, m;
bool adj[MAXN][MAXN];
int cnt[MAXN];
char order[MAXN];
int topoSort()
{
int i, j, k;
memset(cnt, 0, sizeof(cnt));
memset(order, ‘\0‘, sizeof(order));
bool flag = true;
/*统计入度*/
for (i = 1; i <= n; i++) {
for (j = 1; j <= n; j++) {
if (adj[i][j]) {
cnt[j]++;
}
}
}
for ( i = 1; i <= n; i++) {
k = 0;
for (j = 1; j <= n; j++) {
if (cnt[j] == 0) {
if (k == 0) {
k = j;
} else {
flag = false; //入度为零的点不唯一
}
}
}
if (k == 0) {
return 0; //存在环
}
cnt[k] = -1;
order[i - 1] = k + ‘A‘ - 1;
for (j = 1; j <= n; j++) {
if (adj[k][j]) {
cnt[j]--; //k指向的所有节点入度-1
}
}
}
if (flag) {
return 1;
} else {
return 2;
}
}
int main()
{
int u, v;
int result;
char s[10];
int i;
while (scanf("%d %d", &n, &m) && n + m) {
memset(adj, false, sizeof(adj));
bool flag = false;
for (i = 1; i <= m; i++) {
scanf("%s", s);
if (flag) {
continue;
}
u = s[0] - ‘A‘ + 1;
v = s[2] - ‘A‘ + 1;
adj[u][v] = true;
result = topoSort();
if (result == 0) {
printf("Inconsistency found after %d relations.\n", i);
flag = true;
} else if (result == 1) {
printf("Sorted sequence determined after %d relations: %s.\n", i, order);
flag = true;
}
}
if (!flag) {
printf("Sorted sequence cannot be determined.\n");
}
}
return 0;
}
标签:
原文地址:http://www.cnblogs.com/subrshk/p/4240707.html