这是一道拓扑排序的问题。
感觉到自己的脑子像是生锈了一样!
题目描述:
做这道题的时候,题目的意思纠结了好久。三种情况之间的关系,纠结了好久。后来wa了一次,两个原因,一个是因为输出排序的时候那个小点点忘记打印上去了,另一个是Inconsistency和cannot be determined的优先级搞错了。总之,就是题目读得很模糊,题意理解得不够清晰。下面就仔细得把这道题的要求写出来:
给定一些关系,其中关系的对象就是大写字母,没有其他。让你根据这些关系求解;输出的要求分为三种:
有特定的顺序的(这里特定是指唯一的顺序,可以确定的唯一排序)
图中有环的
无法确定唯一顺序的
*注意,这三个要求都是建立在按照给出条件顺序来执行的,也就是比如第一个例子,到第4个表达式就可以确定了,后面条件表达式会造成什么样的结果忽略不计,然后第2个是到第2个条件表达式发现了矛盾,最后一个是当条件都全部给出后,还是无法确定唯一顺序,所以可以写出优先级——>(特定顺序==矛盾)> 无法确定!这个顺序很重要
然后,如何判断有矛盾:用队列的话就是当队列为空的时候,还有元素没有被遍历到
如何判断不唯一:在队列算法进行到任何时候,当出现两个以上入度为0的点
如何判断序列排好:没有矛盾&&从未出现两个或两个以上的点入度为0&&全部的点都被遍历过(0-n)
反思:第一:要认真分析题目 第二:要仔细检查输出 第三:刷题和思考是不可以间断的
最后,加油!
核心代码:
int n, m, num, ax, mp[30][30], en[30], ren[30]; char ans[30]; bool vis[30]; bool circle, cannot; int Toposort(int tn) { queue<int> Q; cannot = false; memset(ans, 0, sizeof(ans)); memset(vis, 0, sizeof(vis)); memset(ren, 0, sizeof(ren)); for ( int i = 1; i <= tn; ++i ) if ( en[i] == 0 ) Q.push(i); //printf("%d\n", Q.size()); if ( Q.size() > 1) cannot = true; if ( Q.size() == 0 ) return 0; int tmp = 1; while( !Q.empty() ) { int x = Q.front(); Q.pop(); int num = 0; vis[x] = true; ans[tmp-1] = x - 1 +'A'; //printf("%c\n", ans[tmp]); for ( int i = 1; i <= n; ++i ) { if ( mp[x][i] && !vis[i] ) { ren[i]++; if ( en[i] == ren[i] ) { num++; if ( num > 1 ) cannot = true; Q.push(i); tmp++; } } } } for ( int i = 1; i <= tn; ++i ) if ( !vis[i] ) return 0; if ( cannot ) return -1; if ( tn == n ) return n; return tmp; } int main() { while (scanf("%d%d", &n, &m) != EOF && ( n != 0 || m != 0 )) { bool flag = true; int tn = 0; memset(mp, 0, sizeof(mp)); memset(en, 0, sizeof(en)); for ( ax = 1; ax <= m; ++ax ) { getchar(); char u, v, op; scanf("%c%c%c", &u, &op, &v); int tu = u-'A'+1, tv = v-'A'+1; if ( tn < tu ) tn = tu; if ( tn < tv ) tn = tv; mp[tu][tv] = 1; en[tv]++; if ( flag ) { int Topo = Toposort(tn); if ( Topo == 0 ) { flag = false; printf("Inconsistency found after %d relations.\n", ax); } else if ( Topo == n ) { flag = false; printf("Sorted sequence determined after %d relations: ", ax); printf("%s.\n", ans); } } } if ( flag ) printf("Sorted sequence cannot be determined.\n"); } }