[圖] 3.2.2 Tarjan演算法-有向圖的強連通分量
阿新 • • 發佈:2018-12-15
Tarjan演算法
【Tarjan演算法】基於對圖DFS的演算法,每個強連通分量為搜尋樹中的一棵子樹
【輔助資料結構】
- DFN[u]:為節點u搜尋的次序編號(時間戳)
- Low[u]:u或u的子樹能夠追溯到的最早棧中結點的次序號
Low(u)=Min {
DFN(u),
Low(v), (u,v)為樹枝邊,u為v的父節點
DFN(v), (u,v)為指向棧中節點的後向邊(非橫叉邊)
} //三個值的最小值
【特殊情況】DFN(u)=Low(u):以u為根的搜尋子樹上所有節點是一個強連通分量。搜尋時,把當前搜尋樹中未處理的節點加入一個堆疊,回溯時可以判斷棧頂到棧中的節點是否為一個強連通分量
tarjan(u) { //虛擬碼 DFN[u]=Low[u]=++Index // 為節點u設定次序編號和Low初值 Stack.push(u) // 將節點u壓入棧中 for each (u, v) in E // 列舉每一條邊 if (v is not visted) // 如果節點v未被訪問過 tarjan(v) // 繼續向下找 Low[u] = min(Low[u], Low[v]) else if (v in S) // 如果節點v還在棧內 Low[u] = min(Low[u], DFN[v]) if (DFN[u] == Low[u]) // 如果節點u是強連通分量的根 repeat v = S.pop // 將v退棧,為該強連通分量中一個頂點 print v until (u== v) }