1. 程式人生 > 其它 >《演算法圖解》第六章 廣度優先搜尋

《演算法圖解》第六章 廣度優先搜尋

一、廣度優先搜尋(breadth-firsh search,BFS)

  =>可回答問題:①從節點A出發,有前往節點B的路徑嗎?②從節點A出發,前往節點B的哪條路徑最短?

  =>最短路徑問題(shorterst-path problem):簡歷模型,再使用廣度優先搜尋來解決。

二、圖

(1)組成:節點(node)、邊(edge)

(2)鄰居:一個節點可能與總多的節點連線,這些節點被稱為鄰居。

(3)實現圖:散列表的對映關係,由於散列表是無序的,鍵值對的新增順序並不影響。

graph={}
# “you”對映到一個數組,包括了“you”的所有鄰居
graph["you"]=["
alice","bob","claire"]

(4)類別:

  =>有向圖(directed graph):邊為箭頭,箭頭的方向指定了關係的方向。關係是單向的,被指向的節點是指向節點的鄰居,注意當沒有互相指向時,並不互為鄰居的。

  =>無向圖(undirected graph):沒有箭頭,關係是雙向的,直接相連的節點互為鄰居。

(5) 實現演算法:

from collections import deque
def person_is_seller(name):
    return name[-1]=='m'
def search(name):
    # 建立一個佇列
search_queue=deque() # 將鄰居都加入這個搜尋隊列中 search_queue+=graph["you"] # 這個陣列用於記錄檢查過的人 searched=[] while search_queue: person=search_queue.popleft() # 僅當這個人沒檢查時才檢查 if not person in searched: if person_is_seller(person): print(person+"
is a mango seller~!") else: search_queue+=graph[person] # 將這個人標記為檢查過 searched.append(person) return False graph={} graph["you"]=["alice","bob","claire"] graph["bob"]=["anuj","peggy"] graph["alice"]=["peggy"] graph["claire"]=["thom","jonny"] graph["anuj"]=[] graph["peggy"]=[] graph["thom"]=[] graph["jonny"]=[] search("you")

  *** 按加入順序檢查搜尋列表中的人,否則找到的就不是最短路徑,因此搜尋列表必須是佇列。

  *** 對於檢查過的人,務必不要再去檢查,否則可能導致無限迴圈。

(6)執行時間:O(人數+邊數)=O(V+E),其中V為頂點數,E為邊數

(7)拓撲排序:A依賴於B,則A必須在B後,這是有序的。

三、佇列(queue)

(1)【入隊 / 壓入 】和 【出隊 / 彈出】:先進先出(First In Frist Out,FIFO)

(2)與棧的異同:不能隨機地訪問佇列中的元素,棧是後進先出(Last In Frist Out,LIFO)。

三、樹(tree):所有的邊都是向下指,沒有往後指的邊。

  =>樹是圖的子集,樹都是圖,但是圖不一定是樹。

6.1 最短路徑的長度為2

6.2 最短路徑的長度為2

6.3 A不可行:吃早餐依賴於刷牙;B可行;C不可行:起床是起點。

6.4 1起床-2鍛鍊-3洗澡-4刷牙-5穿衣服-6打包午餐-7吃早餐

6.5 A是;B不是;C是。