我正在实施排序。程序从带有ASCII字符的文本文件中读取。每行有两个元素,用空格分隔。假设输入是“a b”。这定义了a和b之间的优先关系,称“必须在b之前发生”。
所以如果文件是
a b d c b d
输出
a b d c
我创建了两个链接列表
bigList
:存储唯一元素(count
以跟踪前面的元素)smallList
:存储前面的元素我的代码所做的总结
它实际上打印出文件中的所有元素,就像上面的输入一样,我的输出是
a b b d d c
我是C编程的新手,请让我知道我做错了什么。
答案 0 :(得分:2)
我不太了解拓扑排序,但我认为我足够了解一个明智的评论。任何人都可以随意编辑此回复。
我看到这个实现有几个问题。一些与C相关,其他与算法有关,所以让我一次一个地浏览它们。
问题定义。 Topological sort确实被定义为有向图中元素的优先级。但是,仅这句话并没有完全定义问题。具体来说,拓扑排序是图形元素的优先级,从指定的源顶点开始。举个例子,假设您有以下有向图:
a -> b
b -> c
c -> a
如果从顶点a
开始,则拓扑排序应为{a, b, c}
。如果您从顶点c
开始,则拓扑顺序应为{c, a, b}
。因此,没有源顶点,问题定义就毫无意义。这种顶点的一个选择可能是图形的某个顶点没有边缘指向它,即每个入射边缘都是一个输出边缘。
要记住的另一件事是图connectedness。并不总是可以从任何其他顶点到达任何顶点。因此在实施此类算法时请记住这一点。
良好的数据结构是良好算法的关键。
如果要对有向图中的事物进行排序,最好的办法是创建有向图数据结构,该结构本身将涉及创建Node
数据结构和Edge
数据结构。我建议查找adjacency lists。一旦你有了这样的数据结构,就可以在图表上运行breadth first search,你可以获得拓扑优先权。
实现邻接列表时,您仍需要将所有元素存储在一个位置。链表通常不是最好的方法,因为它需要一个时间来插入一个(假设对数据进行排序),需要线性时间来搜索一个。那是不理想的。正如@ David RF建议的那样,Red-Black trees和AVL trees将成为可能。但是,我不会从这个优化开始。只要您拥有完善的工作算法,就可以随时改进存储数据结构。毕竟,链接列表和搜索树的界面是相同的。
考虑到您使用正确的算法,算法可以很快。 我没有在实践中处理拓扑问题,所以我不知道每一个错综复杂和每一个边缘情况。但!如果使用传统的节点边缘数据结构进行广度优先搜索(请注意边缘可以在节点内隐式定义),搜索本身应该使用广度优先搜索来获取线性时间。
我已经阅读了你的算法,我不得不承认我并没有完全掌握你的大名单和小名单的概念。模棱两可的名字并没有真正帮助。也许它可以通过一个隐藏在某个地方的小小虫来完成工作,但它不太可读。也许其他人可以评论您当前的实施情况。