1. 程式人生 > >回溯法理解

回溯法理解

回溯法

基本思想:

構建問題的解空間樹,在其解空間樹中,從根節點出發,進行深度優先搜尋。在搜尋過程中,對解空間

樹的每個結點進行判斷,判斷該結點是否包含問題的解,若肯定不包含,則跳過對以該結點為根的子樹的

搜尋,逐層向其祖先結點回溯。否則,則進入該子樹,繼續按深度優先策略搜尋。

步驟:

1、針對所給問題,定義其解空間

2、確定易於搜尋的解空間結構

3、深度優先搜尋其解空間,並在搜尋過程中用剪枝函式避免無效搜尋

剪枝:

回溯法搜尋空間樹時,常用限界函式和約束函式避免無效搜尋,其中約束函式將不滿足約束的子樹剪去,限界函式將得不到

最優解的子樹。一般可以利用這兩種剪枝方式提升演算法的效率,避免大量的不必要搜尋。

常見解空間:

常見的解空間有子集樹和排列樹兩種,當問題是從n個元素的集合S中找到滿足某種性質的s的子集時,相應的解空間為子集樹,

通常存在2n個葉結點。0-1揹包的問題相應解空間即為子集樹。當問題是確定n個元素的滿足某種性質的序列時,相應的解空間樹為排列樹

通常有n!個葉結點。旅行售貨問題的解空間即為排列樹。

個人理解:

學習了回溯法後,個人感覺回溯法就是通過對解空間的遍歷,在解空間不斷更新答案,最後找到最優的結果。回溯法最主要的是三點,

一是構造問題的解空間,不同問題的解空間不同,同一個問題也可以構造不同的解空間,最適合的解空間是便通過於搜尋找到答案的一種。

二是搜尋策略,回溯法用的是深度優先搜尋策略,在回溯是需要注意對一些變數的處理操作。三是剪枝,剪枝是回溯法的精髓所在,通過剪

枝去掉大量不必要的搜尋可以大幅的提高演算法的效率,因此回溯法構造合理的剪枝方式可以決定演算法的優劣,十分重要。

例題說明:

7-1 子集和問題 

問題描述:存在一個正整數集合S={x1,x2,…,xn},c是一個整數,判讀S是否存在一個子集s1,子集的和等於c

//輸入
5 10                //5個數字的集合S   c為10
2 2 6 5 4
//輸出
2 2 6         

解空間:

子集和問題的解空間為子集樹結構。其中子集樹的每一層表示是否選擇該數值。

約束函式:

當遞迴的層數大於等於n時,表示當前層次已經大於元素的個數,接下來的為無用搜索,直接剪去該結點的搜尋即可

當搜尋到當前結點後所得的值大於題目中的c,則表示接下來的搜尋不可能找到等於c的答案,直接剪去以該節為根的子樹

的搜尋即可。

if(i>=n||c<ans)    //ans為遍歷到該節點時,所選擇的元素的和
    return;              

if(ans+a[i]<=c)    //第i個元素是否加入子集
if(ans<=c)    

結對程式設計以及學習心得:

在本章學習中,瞭解了回溯法的基本用法,對於大部分的題目中,都可以利用回溯法來解出他的答案,主要

難點是構造解空間和搜尋時的剪枝的方法,剪枝的方法會影響到演算法的最終效率,需要多加考慮。在本次結對程式設計

中,還是存在一些小問題,對同一題的不同想法等,在不斷的交流中加深了對回溯法的理解,對學習理解有一定的幫助

促進效果。