backtracking也是一種程式設計思想,使用到了遞迴。
backtracking要解決的問題大致具有這樣的特徵,為了得到問題的解,需要進行若干步驟,每一步的抉擇都是相同的,每一步都是在上一步的基礎上完成的,需要記錄之前的軌跡,直到終點情況,不過有可能是正確也有可能是錯誤。比如最典型的n皇后問題。需要部署n個皇后,每一次部署都有n種可能。
其程式在實現上滿足下列特徵:
(1)每一步的處理,先check特殊情況,即return case;這裡必須有returncase。
(2)再使用乙個for迴圈,嘗試每一種選擇,在for迴圈內,先檢測該種選擇是否正確,然後如果正確,就在軌跡上記錄,然後遞迴地處理下一步,處理完以後,再把軌跡恢復,供下一中選擇進行。這裡恢復軌跡是很重要的。
可以分為兩類,一種是尋找全部的解,一種是找到乙個解。
乙個解:遞迴函式需要返回值,在for迴圈裡面嘗試每一種可能時,如果該選擇返回true,那麼就返回。否則for結束的時候(執行到這裡說明所有嘗試都失敗了)要返回false。利用返回值可以讓程式提前返回,只找到乙個解。
多個解:這時遞迴函式可以是void型別,這樣就可以搜全部的解,for迴圈結束也不需要處理。
和dp的比較:這裡是指up到bottom遞迴地dp,二者都涉及了遞迴,但是有差別,dp的遞迴是小規模的遞迴,即解決乙個子問題。但是回溯的遞迴是每一步的選擇,可以看成是並列的,都是在一次完整的搜尋中的一步。而且dp是從高到低遞迴,而回溯是從開始到結束,有點從低到高的感覺。
目前為止,涉及到遞迴地思路有分治法,子問題,dp和回溯。很相近,不過還是有差別。
分治法的子問題不重合,子問題是不帶memo的dp,回溯需要記錄軌跡。這些事他們的特徵。
回溯法用於搜尋解,dp找最優解。
下面上乙個n皇后的**,回溯的思路體現的很清晰。包括軌跡和恢復。
public list> solvenqueens(int n)
}solveq(result, cash, 0, n);
return result;
} public void solveq(list> result, char cash, int row, int n)
r.add(s);
}result.add(r);
return;
} for(int i = 0; i < n; i++)
} }private boolean isright(char cash, int row, int col, int n)
int x = row, y = col;
while(x >= 0 && y >= 0)
x = row;y = col;
while(x >= 0 && y < n)
return true;
}
資料結構與演算法 演算法 演算法和資料結構
資料結構與演算法 演算法 好吧,在這裡,您被優秀或優秀的軟體開發人員所隔開。在這種情況下,我會告訴您一開始或至少在我的情況下,並且我知道大多數時候,對於我認識的大多數人,您會覺得自己是乙個無能的人或白痴。基本上,我怎麼可能不理解這一點,然後您會感到沮喪。在這種情況下,我會告訴您情況並不像您想的那麼糟...
資料結構 資料結構與演算法01
1 求一組整數中的最大值。演算法 基本操作是 比較兩個數的大小 模型 仔細想想 你並不知道這個整數到底是多大?整數過大你該怎麼去表示?2 足協的資料庫管理的程式 演算法 需要管理的專案?如何管理?使用者介面?模型 3 資料與資料結構 資料 所有能被輸入到計算機中,並被計算機處理的符號的集合計算機操作...
資料結構 資料結構與演算法02
1 演算法設計的原則 設計演算法時,通常應考慮達到以下目標 1,正確性 2,可讀性 3,健壯性 4,高效率與低儲存量需求 1,正確性 規格說明 四個層次 a,程式中不含語法錯誤 b,程式對於幾組輸入資料能夠得出滿足要求的結果 c,程式對精心選擇的 典型 苛刻切帶有刁難性的幾組輸入資料能夠得出滿足要求...