其他分享
首页 > 其他分享> > 拓扑排序(TopologicalSort)

拓扑排序(TopologicalSort)

作者:互联网

一、拓扑排序(TopologicalSort)

  所谓拓扑排序,就是指在一个有向无环图中,每个顶点都有出现的顺序,然后使得每个顶点都能出现。这里顶点可以看成是一个活动。

  比如说我们要准备学校的运动会

    首先我们要干嘛。。。

    其次我们才能干嘛。。

    。。。。。。。。。。

    。。。。。。。。。。

    最后我们才能干嘛

  为了解决这类问题,于是拓扑排序就产生了。

二、基本思想

  比如说一条边(v1,v2),我们要先进行v1这个活动,然后进行v2这个活动,那么此时v1的入度为0,v2的入度为1,我们要首先输出v1,然后v2的入度为0了,就可以输出了。

    于是乎,就总结除了一条规则,首先找到入度为0的点,就如队列,然后把以入度为0的点作为弧尾的边删除,也就是把以v1为弧尾的点的入度减1,因为我们要删除这几条边对吧?、

  我这里是用邻接表实现的

三、代码实现

 1 #include "bits/stdc++.h"
 2 using namespace std;
 3 int indegree[110];
 4 int n,m;
 5 list <int> adj[110];//创建邻接表 时间复杂度为O(v + e) v是定点数,e是边数
 6 void Topological_Sort()
 7 {
 8     int cnt = 0;
 9     queue <int> ans;
10     for(int i = 1;i <= n;i++)//把入度为0的加入队列
11         if(!indegree[i])
12             ans.push(i);
13     while(!ans.empty()) {
14         int v = ans.front();
15         ans.pop();
16         cout << v << "-->";//输出入度为0的点
17         cnt++;
18         for(auto iter = adj[v].begin();iter != adj[v].end();iter++)//遍历一v为弧尾的边,并减去对应顶点的入度,把入度为0的加入队列
19             if(!(--indegree[*iter]))
20                 ans.push(*iter);
21     }
22     if(cnt < n) 
23         cout << "\nLoop!" << endl;
24     else 
25         cout << "\nSuccessful!" << endl;
26 }
27 int main()
28 {
29     cin >> n >> m;
30     for(int i = 1;i <= m;i++){
31         int sx,sy;
32         cin >> sx >> sy;
33         indegree[sy]++;//sy入度+1
34         adj[sx].push_back(sy);
35     }
36     Topological_Sort();
37     return 0;
38 }
39 /*
40     test case:
41         6 6
42         6 3
43         6 1
44         5 1
45         5 2
46         3 4
47         4 2
48         动图网址:https://www.cs.usfca.edu/~galles/visualization/TopoSortIndegree.html
49 */

标签:int,拓扑,入度,v2,iter,v1,TopologicalSort,排序,adj
来源: https://www.cnblogs.com/scannerkk/p/15859763.html