poj 1094 Sorting It All Out 拓扑排序
poj 1094 Sorting It All Out 拓扑排序
//poj 1094 Sorting It All Out 拓扑排序 //这题要先判断是否有环的存在(可以用floyd算法看有没有能到自己的结点来判断, //也可以把度数为0的点一个一个排除,直到没有结点为止,若还有结点没排除,且 //没有度数为0的点,则表示有环存在),然后判断是否有多个度数为0的结点, //若上述两种情况都没有,则表示找到解 #include <stdio.h> #include <string.h> #define N 30 int n, m; int deg[N], ans[N], tmp_d[N]; bool map[N][N]; int toposort() { for(int i = 0; i < n; ++i) tmp_d[i] = deg[i]; int cnt = 0, flag2 = 1; //flag2初始值为1表示找到解, //若flag2为-1时表示有多个度数为0的结点,这时要先排除没有环存在 //即不能仅仅找到有两个以上的结点的度数为0就返回-1,而要把这些结点 //的度数设为-1后继续找度数为0的结点,若n个结点都遍历过一次则表示没有环 //若还没遍历完却没有度数为0的点了的时候表示有环 //如数据:4 4 A<B C<B D<B B<A for(int i = 0; i < n; ++i) { int n_0deg = 0, deg0; for(int j = 0; j < n; ++j) { if(tmp_d[j] == 0) { n_0deg++; //记录有几个度数为0的结点 deg0 = j; //记录度数为0的结点 } } if(n_0deg == 0) //若没找到度数为0的结点则表示有环 return 0; if(n_0deg > 1) //找到不止一个度数为0的结点 flag2 = -1; tmp_d[deg0] = -1; for(int j = 0; j < n; ++j) if(map[deg0][j] == true) tmp_d[j]--; ans[cnt++] = deg0; } return flag2; //n个结点都排好序 } int main() { //freopen("in.txt", "r", stdin); char s[4]; while(scanf("%d%d", &n, &m), n||m) { memset(map, false, sizeof(map)); memset(deg, 0, sizeof(deg)); int step = 0, flag1 = 0; //flag1初始化为0表示还没找到解 for(int i = 1; i <= m; ++i) { scanf("%s", s); int a = s[0] - 'A', b = s[2] - 'A'; if(map[a][b] == false) { map[a][b] = true; deg[b]++; } int res = toposort(); if(flag1 == 1) //若flag1为1时表示已找到解 continue; if(res == 0) //若返回0表示有环 { flag1 = 1; printf("Inconsistency found after %d relations.\n", i); } if(res == 1) //res为1表示找到解了 { step = i; //记录第几步 flag1 = 1; //找到解 printf("Sorted sequence determined after %d relations: ", i); for(int j = 0; j < n; ++j) putchar(ans[j] + 'A'); puts("."); } } if(flag1 == 0) //若flag1为0表示找不到解 puts("Sorted sequence cannot be determined."); } return 0; }