利用Gabow算法求有向图的强连通分量
论文写作或者计算需要帮助可发邮件到 hwstu # sohu.com 把 #替换成@,请说清来意,不必拐弯抹角,浪费相互之间的时间。
返回首页
此处输入要素的个数:
Gabow算法是用于求有向图的强连通分量
Gabow算法的用途之一是,求一个有向图G=(V,E)里极大强连通分量。强连通分量是指有向图G里顶点间能互相到达的子图。而如果一个强连通分量已经没有被其它强通分量完全包含的话,那么这个强连通分量就是极大强连通分量。
时间复杂度:O(M+N) 注:M代表边数,N代表顶点数。
步骤概要:
步骤1: 找一个没有被遍历过的顶点v,进行步骤2(v)(遍历时间由1开始累加,若是非连通图,则须重复进行步骤1)。否则,算法结束。
步骤2 将v压入堆栈stk1[]和stk2[];
对于v所有的邻接顶点u:
(1) 如果u没有被遍历过,则进行步骤2(u),同时维护stk2[]
(2) 如果u已经被遍历过,如果访问过,但没有删除,维护stk2[](处理环的过程,在stk2 中删除构成环的节点)
如果stk2[]的顶元素==v,那么输出相应的强连通分量
简要说明:
这个算法其实就是Tarjan算法的变异体,我们观察一下,只是它用第二个堆栈来辅助求出强连通分量的根,而不是Tarjan算法里面的DFN[]和Low[]数组。那么,我们说一下如何使用第二个堆栈来辅助求出强连通分量的根。
我们使用类比方法,在Tarjan算法中,每次Low[i]的修改都是由于环的出现(不然,Low[i]的值不可能变小),每次出现环,在这个环里面只剩下一个Low[i]没有被改变(深度最低的那个),或者全部被改变,因为那个深度最低的节点在另一个环内。那么Gabow算 法中的第二堆栈变化就是删除构成环的节点,只剩深度最低的节点,或者全部删除,这个过程是通过出栈来实现,因为深度最低的那个顶点一定比前面的先访问,那 么只要出栈一直到栈顶那个顶点的访问时间不大于深度最低的那个顶点。其中每个被弹出的节点属于同一个强连通分量。那有人会问:为什么弹出的都是同一个强连 通分量?因为在这个节点访问之前,能够构成强连通分量的那些节点已经被弹出了,这个对Tarjan算法有了解的都应该清楚,那么Tarjan算法中的判断根我们用什么来代替呢?想想,其实就是看看第二个堆栈的顶元素是不是当前顶点就可以了。
现在,你应该明白其实Tarjan算法和Gabow算法其实是同一个思想的不同实现,但是,Gabow算法更精妙,时间更少(不用频繁更新Low[])。
显示的是一个随机 12 * 12 的方阵
|
老鼠 | 金牛 | 白虎 | 狡兔 | 青龙 | 毒蛇 | 骏马 | 小羊 | 猕猴 | 山鸡 | 狗仔 | 笨猪 |
老鼠 |
|
|
|
|
1 |
|
|
1 |
|
|
|
|
金牛 |
|
|
1 |
|
1 |
1 |
|
|
|
|
|
|
白虎 |
|
1 |
|
|
1 |
|
|
|
|
|
1 |
|
狡兔 |
|
|
|
|
|
|
|
|
|
|
|
|
青龙 |
|
|
1 |
|
|
|
|
|
1 |
|
1 |
1 |
毒蛇 |
|
|
|
|
|
|
|
|
|
1 |
|
|
骏马 |
|
|
|
|
|
|
|
|
|
|
1 |
|
小羊 |
|
|
|
1 |
|
|
|
|
1 |
|
|
|
猕猴 |
|
|
|
|
|
|
|
|
|
|
|
|
山鸡 |
|
|
1 |
1 |
|
|
|
|
|
|
|
|
狗仔 |
|
|
|
|
|
|
|
|
|
|
|
|
笨猪 |
|
1 |
|
|
|
|
|
|
|
|
|
|
开始用深度搜索,从第一个节点开始!
访问的元素是:老鼠
搜索树里的元素的顺序是:老鼠=>1
堆栈stack_1里的元素有:老鼠
堆栈stack_path要素有:老鼠
访问的元素是:青龙
搜索树里的元素的顺序是:老鼠=>1、青龙=>2
堆栈stack_1里的元素有:老鼠、青龙
堆栈stack_path要素有:老鼠、金牛
访问的元素是:白虎
搜索树里的元素的顺序是:老鼠=>1、青龙=>2、白虎=>3
堆栈stack_1里的元素有:老鼠、青龙、白虎
堆栈stack_path要素有:老鼠、金牛、白虎
访问的元素是:金牛
搜索树里的元素的顺序是:老鼠=>1、青龙=>2、白虎=>3、金牛=>4
堆栈stack_1里的元素有:老鼠、青龙、白虎、金牛
堆栈stack_path要素有:老鼠、金牛、白虎、狡兔
注意:金牛 的值为 4 大于白虎的值3
弹出堆栈stack_path要素:金牛
注意:白虎 的值为 3 大于青龙的值2
弹出堆栈stack_path要素:白虎
访问的元素是:毒蛇
搜索树里的元素的顺序是:老鼠=>1、青龙=>2、白虎=>3、金牛=>4、毒蛇=>5
堆栈stack_1里的元素有:老鼠、青龙、白虎、金牛、毒蛇
堆栈stack_path要素有:老鼠、金牛、白虎
访问的元素是:山鸡
搜索树里的元素的顺序是:老鼠=>1、青龙=>2、白虎=>3、金牛=>4、毒蛇=>5、山鸡=>6
堆栈stack_1里的元素有:老鼠、青龙、白虎、金牛、毒蛇、山鸡
堆栈stack_path要素有:老鼠、金牛、白虎、狡兔
注意:山鸡 的值为 6 大于白虎的值3
弹出堆栈stack_path要素:山鸡
弹出堆栈stack_path要素:毒蛇
访问的元素是:狡兔
搜索树里的元素的顺序是:老鼠=>1、青龙=>2、白虎=>3、金牛=>4、毒蛇=>5、山鸡=>6、狡兔=>7
堆栈stack_1里的元素有:老鼠、青龙、白虎、金牛、毒蛇、山鸡、狡兔
堆栈stack_path要素有:老鼠、金牛、白虎
弹出堆栈stack_path要素:狡兔
弹出堆栈stack_1要素:狡兔
访问的元素是:狗仔
搜索树里的元素的顺序是:老鼠=>1、青龙=>2、白虎=>3、金牛=>4、毒蛇=>5、山鸡=>6、狡兔=>7、狗仔=>8
堆栈stack_1里的元素有:老鼠、青龙、白虎、金牛、毒蛇、山鸡、狗仔
堆栈stack_path要素有:老鼠、金牛、白虎
弹出堆栈stack_path要素:狗仔
弹出堆栈stack_1要素:狗仔
访问的元素是:猕猴
搜索树里的元素的顺序是:老鼠=>1、青龙=>2、白虎=>3、金牛=>4、毒蛇=>5、山鸡=>6、狡兔=>7、狗仔=>8、猕猴=>9
堆栈stack_1里的元素有:老鼠、青龙、白虎、金牛、毒蛇、山鸡、猕猴
堆栈stack_path要素有:老鼠、金牛、白虎
弹出堆栈stack_path要素:猕猴
弹出堆栈stack_1要素:猕猴
访问的元素是:笨猪
搜索树里的元素的顺序是:老鼠=>1、青龙=>2、白虎=>3、金牛=>4、毒蛇=>5、山鸡=>6、狡兔=>7、狗仔=>8、猕猴=>9、笨猪=>10
堆栈stack_1里的元素有:老鼠、青龙、白虎、金牛、毒蛇、山鸡、笨猪
堆栈stack_path要素有:老鼠、金牛、白虎
注意:笨猪 的值为 10 大于金牛的值4
弹出堆栈stack_path要素:笨猪
弹出堆栈stack_path要素:青龙
弹出堆栈stack_1要素:笨猪
弹出堆栈stack_1要素:山鸡
弹出堆栈stack_1要素:毒蛇
弹出堆栈stack_1要素:金牛
弹出堆栈stack_1要素:白虎
弹出堆栈stack_1要素:青龙
访问的元素是:小羊
搜索树里的元素的顺序是:老鼠=>1、青龙=>2、白虎=>3、金牛=>4、毒蛇=>5、山鸡=>6、狡兔=>7、狗仔=>8、猕猴=>9、笨猪=>10、小羊=>11
堆栈stack_1里的元素有:老鼠、小羊
堆栈stack_path要素有:老鼠、金牛
弹出堆栈stack_path要素:小羊
弹出堆栈stack_1要素:小羊
弹出堆栈stack_path要素:老鼠
弹出堆栈stack_1要素:老鼠
访问的元素是:骏马
搜索树里的元素的顺序是:老鼠=>1、青龙=>2、白虎=>3、金牛=>4、毒蛇=>5、山鸡=>6、狡兔=>7、狗仔=>8、猕猴=>9、笨猪=>10、小羊=>11、骏马=>12
堆栈stack_1里的元素有:骏马
堆栈stack_path要素有:老鼠
弹出堆栈stack_path要素:骏马
弹出堆栈stack_1要素:骏马
|
狡兔 |
狗仔 |
猕猴 |
笨猪 |
山鸡 |
毒蛇 |
金牛 |
白虎 |
青龙 |
小羊 |
老鼠 |
骏马 |
狡兔 | |
|
|
|
|
|
|
|
|
|
|
|
狗仔 | |
|
|
|
|
|
|
|
|
|
|
|
猕猴 | |
|
|
|
|
|
|
|
|
|
|
|
笨猪 | |
|
|
|
|
|
1 |
|
|
|
|
|
山鸡 | 1 |
|
|
|
|
|
|
1 |
|
|
|
|
毒蛇 | |
|
|
|
1 |
|
|
|
|
|
|
|
金牛 | |
|
|
|
|
1 |
|
1 |
1 |
|
|
|
白虎 | |
1 |
|
|
|
|
1 |
|
1 |
|
|
|
青龙 | |
1 |
1 |
1 |
|
|
|
1 |
|
|
|
|
小羊 | 1 |
|
1 |
|
|
|
|
|
|
|
|
|
老鼠 | |
|
|
|
|
|
|
|
1 |
1 |
|
|
骏马 | |
1 |
|
|
|
|
|
|
|
|
|
|
计算出来后的
化学加平台
解释结构模型
感谢化学加提供单独服务器服务器!请大家多支持化学加平台,可以多介绍人关注化学加!
对解释结构模型在线计算有什么意见与建议请发电子邮件到, hwstu #sohu.com 把#替换成 @