演算法 搜尋演算法 盲目搜尋和啟發式搜尋

2021-10-04 02:27:49 字數 2899 閱讀 9648

對乙個圖進行搜尋意味著按照某種特定的順序依次訪問其頂點。在所有搜尋方式中,廣度優先演算法和深度優先搜尋演算法都十分重要,因為它們提供了一套系統地訪問圖資料結構的方法。我們著重講解廣度優先搜尋演算法。

具體例子可看以下文章:

廣度和深度解析

深度優先搜尋演算法(簡稱dfs)是一種用於遍歷或搜尋樹或圖的演算法。沿著樹的深度遍歷樹的節點,盡可能深的搜尋樹的分支。當節點的所在邊都己被探尋過,搜尋將回溯到發現節點的那條邊的起始節點。這一過程一直進行到已發現從源節點可達的所有節點為止。由於深度優先搜尋不是接下來最短路徑演算法的基礎,因此這裡不做拓展。

廣度優先搜尋演算法(簡稱bfs)又稱為寬度優先搜尋從起點開始,首先遍歷起點周圍鄰近的點,然後再遍歷已經遍歷過的點鄰近的點,逐步的向外擴散,直到找到終點。

在執行演算法的過程中,每個點需要記錄達到該點的前乙個點的位置 —父節點。這樣做之後,一旦到達終點,便可以從終點開始,反過來順著父節點的順序找到起點,由此就構成了一條路徑。

以上兩種演算法的不同搜尋策略可以通過下面網頁檢視**,這是兩種相鄰節點之間的移動代價相等時用到的演算法,圖中的邊不設權值。

dijkstra演算法是由計算機科學家edsger w.dijkstra在2023年提出的。

考慮這樣一種場景,在一些情況下,圖形中相鄰節點之間的移動代價並不相等。例如,遊戲中的一幅圖,既有平地也有山脈,那麼遊戲中的角色在平地和山脈中移動的速度通常是不相等的。在dijkstra演算法中,需要計算每乙個節點距離起點的總移動代價。同時,還需要乙個優先佇列結構。對於所有待遍歷的節點,放入優先佇列中會按照代價進行排序。在演算法執行的過程中,每次都從優先佇列中選出代價最小的作為下乙個遍歷的節點。直到到達終點為止。

對比了不考慮節點移動代價差異的廣度優先搜尋與考慮移動代價的dijkstra演算法,又如下**所示:

可以看出當圖形為網格圖,並且每個節點之間的移動代價是相等的,那麼dijkstra演算法將和廣度優先演算法變得一樣。以下**鏈結可以自行設定綠色網格的位置。

dijkstra演算法(可自行設定障礙物)

在dijkstra演算法中,我已經發現了其最終要的缺陷,搜尋存在盲目性。在這裡,我們只針對這個痛點,採用貪婪最佳優先搜尋來解決。如何解決?我們只需稍微改變下觀念即可,在dijkstra演算法中,優先佇列採用的是,每個頂點到起始頂點的預估值來進行排序。在貪婪最佳優先搜尋採用的是,每個頂點到起始頂點的預估值來進行排序。

兩者的搜尋過程對比如下**所示:

明顯看到右邊的演算法(貪婪最佳優先搜尋 )尋找速度要快於左側,雖然它的路徑不是最優和最短的,但障礙物最少的時候,他的速度卻足夠的快。這就是貪心演算法的優勢,基於目標去搜尋,而不是完全搜尋。

貪婪最佳優先搜尋動態圖(可自行設定障礙物)

我們找到了最短路徑和搜尋頂點最少數量的兩種方案,dijkstra 演算法和貪婪最佳優先搜尋。接下來能否汲取兩者的有點選擇既速度快又能得到最優解的演算法?.

a star演算法正是這麼做了,它吸取了dijkstra 演算法中的當前代價,為每個邊長設定權值,不停的計算每個頂點到起始頂點的距離,以獲得最短路線,同時也汲取貪婪最佳優先搜尋演算法中不斷向目標前進優勢,並持續計算每個頂點到目標頂點的距離,以引導搜尋佇列不斷想目標逼近,從而搜尋更少的頂點,保持尋路的最優解。a star演算法在運算過程中,每次從優先佇列中選取f(n)值最小(優先順序最高)的節點作為下乙個待遍歷的節點。a star演算法使用兩個集合來表示待遍歷的節點,與已經遍歷過的節點,這通常稱之為open_set和close_set。

a star演算法優先佇列排序方式基於估價值,估價值由頂點到起始頂點的距離(代價)加上頂點到目標頂點的距離(啟發函式)之和構成。

a star演算法、貪婪最佳優先、dijkstra演算法三者的靜態效果圖如下:

三者動態效果圖對比(可自行設定障礙物)

f(n)=g(n)+h(n)f(n)=g(n)+h(n)

f(n)=g(n)+h(n)

f(n)是節點n的綜合優先順序。當我們選擇下乙個要遍歷的節點時,我們總會選取綜合優先順序最高(值最小)的節點。g(n) 是節點n距離起點的代價。h(n)是節點n距離終點的預計代價,這也就是a star演算法的啟發函式。

上面已經提到,啟發函式會影響a star演算法的行為。

在極端情況下,當啟發函式h(n)始終為0,則將由g(n)決定節點的優先順序,此時演算法就退化成了dijkstra演算法。

如果h(n)始終小於等於節點n到終點的代價,則a star演算法保證一定能夠找到最短路徑。但是當h(n)的值越小,演算法將遍歷越多的節點,也就導致演算法越慢。

如果h(n)完全等於節點n到終點的代價,則a star演算法將找到最佳路徑,並且速度很快。可惜的是,並非所有場景下都能做到這一點。因為在沒有達到終點之前,我們很難確切算出距離終點還有多遠。

如果h(n)的值比節點n到終點的代價要大,則a star演算法不能保證找到最短路徑,不過此時會很快。在另外乙個極端情況下,如果h(n)相較於g(n)大很多,則此時只有h(n)產生效果,這也就變成了貪婪最佳優先搜尋。

由上面這些資訊我們可以知道,通過調節啟發函式我們可以控制演算法的速度和精確度。因為在一些情況,我們可能未必需要最短路徑,而是希望能夠盡快找到乙個路徑即可。這也是a star演算法比較靈活的地方。對於網格形式的圖,有以下這些啟發函式可以使用:

如果圖形中只允許朝上下左右四個方向移動,則可以使用曼哈頓距離。

如果圖形中允許朝八個方向移動,則可以使用對角距離。

如果圖形中允許朝任何方向移動,則可以使用歐幾里得距離。

以下網頁是五種不同搜尋演算法的搜尋過程對比:

五種搜尋演算法(可進行新增多種障礙物)

下面對在有權圖(紫)和無權圖(黃)上利用搜尋演算法的特點做乙個總結:

啟發式搜尋演算法(A 演算法)

a算發 在bfs演算法中,若對每個狀態n都設定估價函式f n g n h n 並且每次從開啟列表中選節點 進行擴充套件時,都選取f值最小的節點,則該搜尋演算法為啟發式搜尋演算法,又稱a演算法。g n 從起始狀態到當前狀態n的代價。h n 從當前狀態n到目標狀態的估計代價。a演算法的例子 八數碼 2 ...

A 演算法(啟發式搜尋)

a 演算法,a a star 演算法是一種靜態路網中求解最短路徑最有效的直接搜尋方法,也是解決許多搜尋問題的有效演算法。演算法中的距離估算值與實際值越接近,最終搜尋速度越快。別稱 啟發式搜尋 表示式 f n g n h n f n g n h n f n g n h n 公式表示為 f n g n ...

演算法初探 啟發式搜尋

2020.07.21 11 40 2020.08.30 16 55 a problem 如果讓你在這麼乙個方格圖中尋找最短路徑,你會怎麼做?student a 我會廣度優先演算法!student b 最優 我會貪心走過去!上面是最簡單的狀況,如果有障礙物呢?注 綠色格仔不可通過 student a ...