poj1094
题意:有一些未知数各不相等,给出一些两两比较的大小关系,问到第几个关系开始可以确定整体排序或出现矛盾,再或者所有关系都用过了也无法确定整体排序。
分析:闭包传递,我们每获得一个比较关系就更新我们已知的关系库,关系库中要记录所有我们现在已知的能比较大小的关系对。一条大小关系a<b的信息可以给我们提供如下信息:
1.a<b
2.所有小于a的未知数都小于b
3.所有大于b的未知数都大于a
4.所有大于b的未知数都大于所有小于a的未知数
利用以上四条信息我们可以获得更多的两两大小关系。判断是否已确定整体排序的方法是,判断我们当前的关系库中是否所有对的大小都已知(因为我们能推断出的关系都在关系库中,如果关系库中没有某对的关系则必然是无法判断导致的)。判断是否出现矛盾的方法是,当我们看到a<b这条输入时,是否关系库中已经有了b<a(我们所有能推断出的东西都在关系库里,与关系库不矛盾则与已知不矛盾)。
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
#include <iostream> #include <cstdlib> #include <cstring> #include <cstdio> #include <algorithm> using namespace std; #define maxn 30 int n, m; bool smaller[maxn][maxn]; enum Result { inconsistent, determined, undetermined }; bool cmp(int a, int b) { return smaller[a][b]; } int get_id(char a) { return a - 'A'; } Result work(int a, int b) { if (smaller[b][a]) return inconsistent; smaller[a][b] = true; for (int i = 0; i < n; i++) if (smaller[i][a]) smaller[i][b] = true; for (int i = 0; i < n; i++) if (smaller[b][i]) smaller[a][i] = true; for (int i = 0; i < n; i++) for (int j = 0; j < n; j++) if (smaller[i][a] && smaller[b][j]) smaller[i][j] = true; for (int i = 0; i < n; i++) for (int j = i + 1; j < n; j++) if (!(smaller[i][j] || smaller[j][i])) return undetermined; return determined; } void input(int x) { char st[5]; for (int i = x + 1; i < m; i++) gets(st); } void output() { int f[maxn]; for (int i = 0; i < n; i++) f[i] = i; sort(f, f + n, cmp); for (int i = 0; i < n; i++) putchar(f[i] + 'A'); } int main() { //freopen("t.txt", "r", stdin); while (scanf("%d%d", &n, &m), n | m) { getchar(); memset(smaller, 0, sizeof(smaller)); Result ans = undetermined; for (int i = 0; i < m; i++) { char a, b, opr; a = getchar(); opr = getchar(); b = getchar(); getchar(); if (opr == '<') ans = work(get_id(a), get_id(b)); else ans = work(get_id(b), get_id(a)); if (ans == inconsistent) { printf("Inconsistency found after %d relations.\n", i + 1); input(i); break; } if (ans == determined) { printf("Sorted sequence determined after %d relations: ", i + 1); input(i); output(); printf(".\n"); break; } } if (ans == undetermined) puts("Sorted sequence cannot be determined."); } return 0; }