迷宮系列(三)利用BFS/DFS的資料得到最短路/通路
阿新 • • 發佈:2019-02-09
一、如何得到最短路
演算法性質分析
1.BFS性質:
該演算法需要在發現所有與這個源節點距離為k的節點後,才回去發現與這個源節點距離為k+1的節點。
故BFS對一個圖G的搜尋是嚴格分層的,如果一個點V在第n層被發現,那麼它距離源節點的最短距離一定為n,否則將違背BFS演算法的性質。
2.DFS性質:
主要思想:一條路走到黑
故:DFS在問題有解的情況下可以順利找到解,但DFS的搜尋是盲目的,它的目的僅僅是走過各種可能的分支來找到問題的解,但不一定是最優解。
比如:DFS演算法第一步就走了錯誤的一步,在此之後即使到達目的節點也不會是最短的路徑
3.結論
BFS演算法可以用來找出一個圖中的最短路
DFS演算法不能找出最短路,但可以找出所有通路(雖然BFS也可以)
二、如何得到路徑
1.考慮在BFS演算法示例中得到的結果
假設起點為A,前往G,顯然最短路有兩條A->D->G和A->E->G
2.如何根據表格裡的資料得到路徑呢
思路1.
從起點A開始搜尋,根據dis遞增的規律來找到G,從而輸出正確的路徑
分析:不可行
原因:從A點出發會產生過多的旁枝,沒有意義
思路2.
從終點G開始逆向搜尋,根據dis遞減的規律來找到A,從而輸出正確的路徑
分析:可行
原因:由於起點是唯一的,從G延展出的所有dis嚴格遞減的節點序列最終一定都回到起點A。
3.如何實現?
做法:搜尋,深度優先搜尋= ̄ω ̄=
虛擬碼
PATH(節點v)
{
if (v == 起點)
{
從棧底輸出棧S,即為最短路徑之一;
}
else
{
for (與v鄰接的每一個元素u)
{
if (u尚未被訪問)
{
if ( u.dis == v.dis - 1) // u是v的前驅(是u發現的v)
{
標記u被訪問;
把u壓入棧;
PATH(u);
取消u的標記;
彈出棧頂元素;
}
}
}
}
}
另:如何尋找通路
對於通路,我們可以認為只要該節點dis屬性不為初始值(-1),這個節點就是可以行走的,所以我們可以從終點起,按照這樣的狀態轉移約束,搜尋出所有的通路