Tarjan的求双连通分量算法
哎~氣死我了!昨天晚上都寫好了……一不小心把網頁關了,寫的全沒了……MD
什么是雙連通分量DCC(Double connected component)?
首先說一下一個無向連通圖,若去掉任一點或任一邊都不影響該圖的連通性(本來是連通的,現在仍連通),那么該圖是一個雙連通圖(該圖的DCC只有一個即本身)。
DCC是一個無向連通圖(注意是無向連通圖不是有向圖,別把強連通分量與他們搞混了!)的子圖,該子圖是一個雙連通圖(盡可能大的雙連通圖,也就是盡可能包含更多的點)。也就是說一個無向連通圖的DCC需要滿足三個條件:1.它是該無向連通圖的子圖 2.該子圖是一個雙連通圖 3.使該子圖盡可能的大
什么是割點、橋?
一個無向連通圖,去掉一點或一邊后影響了改圖的連通性(本來是連通的,現在不連通了),則該點就是割點或該邊就是橋。
求DCC的算法的分析,我就不說了……就是說了也難以理解,直接貼上加注釋的code,你自己畫個圖,跟著程序走一遍,慢慢體會體會!
//----------DCC------------------int dfn[MAXNODE],low[MAXNODE],index;//dfn記錄各點被訪問次序,low是追溯到DCC的根節點
//的dfn的值,當根節點的某個直接兒子節點的low值大于或等于根節點的dfn的值時,就可以從
//棧中取值了,直到取到根節點為止時一個DCC
int stack[MAXNODE],top;//棧:用深搜搜索節點并依次存儲各個節點—以便于找到DCC(即當
//發現環時就是一個DCC,用low標記的,從該棧中取值取到該根節點為止)
int id_dcc[MAXNODE],cnt_dcc;//id_dcc:名副其實即DCC的id(編號),存儲各節點的所在的
//編號(就是你給他們編的號,從1-n)cnt_dcc就是編號下標!
int father[MAXNODE];//由于求DCC是在一個無向連通圖中,即為雙向的圖,該father就是為了
//防止某一節點又訪問上一個節點(上一個節點搜出該節點)
void DFS_DCC(int cur)
{
int next; //next為cur節點下的節點
dfn[cur]=low[cur]=++index;
stack[++top]=cur;
for(Node *p=G[cur];p;p=p->next)
{
next=p->num;
if(!dfn[next])
{
father[next]=cur; //額,可以不用。。
DFS_DCC(next);
if(low[next]<low[cur]) //更新low使每一個DCC中的low的值==根節點low值
low[cur]=low[next];
if(low[next]>=dfn[cur])//當發現節點cur的兒子節點next的low值>=dfn[cur]
{ //則就要取棧,即是時候取出DCC了。為什么?因為不
cnt_dcc++; //這樣就不對了^_^!(具體原因,自己舉幾個例子try)
do
{
next=stack[top--];
id_dcc[next]=cnt_dcc;
}while(next!=cur);
top++; //這里為什么要++因為連著DCC是有共同節點的(舉例try)
//不++肯定要出錯!也許我這code跟別人不一樣,其實
//思想都一樣,只是具體實現的code有小小的差異罷了
}
}
else if(next!=father[cur] && dfn[next]<low[cur])
{
//呃呃呃!其實不用這個father數組都可以了,只需
//dfn[next]<low[cur]就行了
low[cur]=dfn[next];
}
}
}
void solve()
{
index=top=cnt_dcc=0;
memset(dfn,0,sizeof(dfn));//初始化各下標及dfn
DFS_DCC(1);//由于是無向連通圖,只需深搜一個節點就都可以都到了
}
上面的是求DCC,有時候要求割點,求橋,你根據定義自己想想……都差不來啊!
?
可能解釋的不夠清楚,有什么問題?可以問我餓!或者發現有什么不對或不好的地方,歡迎指正!
不過我也只是知道這樣實現,并不真正懂得為什么。你如果問我為什么是這樣,它的原理是什么?我會給你說:因為只有這樣才能實現,它原理就在實現中^_^!如果大蝦你理解的深的話……希望能給小弟分享一下!
轉載于:https://www.cnblogs.com/fornever/archive/2011/09/17/2179448.html
總結
以上是生活随笔為你收集整理的Tarjan的求双连通分量算法的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Flash务实主义(五)——AS3的垃圾
- 下一篇: Oracle数据库设计要做到五戒