[2016-02-18][拓扑排序]
[2016-02-18][拓扑排序]
拓扑排序
- 思路 dfs
- 分析
- 从树的角度来看,就是不同层的节点,顺序是一定的,同层的节点,顺序是不定的,
- 但是拓扑排序的图不一定是树,可以有环(不能是同向的环,即1->2->3->1 这种)
- 为了避免漏了节点,必须枚举每一个点跑一次dfs
- 为了避免出现通向环的情况,必须加上标志,在每次dfs时候,标记非0值表示访问过,但是进入下一层dfs时,标记为-1,如果下层dfs访问到这个节点时的标记为-1,说明有环,出来dfs才设置为1,表示这个点后面没有同向环
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 | const int maxn = 100 + 10;//n表示节点数,m表示边数,g保存有向边的信息,vis保存是否访问过节点,t表示当前拓扑排序的编号,topo保存拓扑排序的结果//注意,这里节点的编号是 1 ~ n int n,m,g[maxn][maxn],vis[maxn],topo[maxn],t;int dfs(int u){ vis[u] = -1; for(int v = 1,;v < n + 1;v++){ if(g[u][v]){ if(vis[v] < 0) return 0; if(!vis[v] && !dfs(v)) return 0; } } vis[u] = 1; topo[--t] = u; return 1;}int toposort(){ t = n; memset(vis,0,sizeof(vis)); //枚举每一个点,如果存在环,就返回0 for(int u = 1;u < n+1;u++){ if(!vis[u] && !dfs(u)) return 0; } return 1;} |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 | const int maxn = 100 + 10;int n,m,g[maxn][maxn],vis[maxn],topo[maxn],t;int dfs(int u){ vis[u] = -1; for(int v = 1,;v < n + 1;v++){ if(g[u][v]){ if(vis[v] < 0) return 0; if(!vis[v] && !dfs(v)) return 0; } } vis[u] = 1; topo[--t] = u; return 1;}int toposort(){ t = n; memset(vis,0,sizeof(vis)); for(int u = 1;u < n+1;u++){ if(!vis[u] && !dfs(u)) return 0; } return 1;} |
浙公网安备 33010602011771号