在了解图的拓扑排序之前我们需要介绍有向图。有向图是指在图中节点和节点之间的连接边是有方向的。有向图的拓扑排序是指对有向图中的节点对其进行现行的排序。如下图中要完成8,必须完成3和7,要完成11必须先完成5和7等等。这些就是节点之间的顺序,如果我们按照从上到下的顺序进行排序是:5,7,3,11,8,2,9,10。这是这个图的一个拓扑排序。
这里我们需要介绍几个概念:
度:依附于某顶点v的变数
入度:以顶点v为终点的弧的数量
出度:以顶点v为起点的弧的数量
求一个图的拓扑排序的算法时间复杂度是O(|V|+|E|),其中|V|是边的数量,|E|是节点的数量。求解一个图的拓扑排序有如下算法:
Kahn算法
该算法首先需要找到图中任意一个入度为0的节点。如果没有则该如不是一个DAG(Directed acyclic graph)无环有向图。
L ← Empty list that will contain the sorted elements
S ← Set of all nodes with no incoming edges
while S is non-empty do
remove a node n from S
add n to tail of L
for each node m with an edge e from n to m do
remove edge e from the graph
if m has no other incoming edges then
insert m into S
if graph has edges then
return error (graph has at least one cycle)
else
return L (a topologically sorted order)
深度优先搜索(DFS)
L ← Empty list that will contain the sorted nodes
while there are unmarked nodes do
select an unmarked node n
visit(n)
function visit(node n)
if n has a temporary mark then stop (not a DAG)
if n is not marked (i.e. has not been visited yet) then
mark n temporarily
for each node m with an edge from n to m do
visit(m)
mark n permanently
unmark n temporarily
add n to head of L