Java遞迴演算法
在程式設計中,遞迴的設計就是利用了棧的“後進先出”的思想。利用棧可以將遞迴程式轉換為非遞迴程式。
3.3.1 遞 歸
遞迴是指在函式的定義中,在定義自己的同時又出現了對自身的呼叫。如果一個函式在函式體中直接呼叫自己,就稱為直接遞迴函式。如果經過一系列的中間呼叫,間接呼叫自己的函式就稱為間接遞迴呼叫。
1. 遞迴函式
例如,n 的階乘遞迴定義如下:
n 的階乘演算法如下:
public static long fact(int n)
//n 的階乘的非遞迴演算法實現
{
long f = 1;
int i;
for(i=1;i<n+1;i++) //
直接利用迭代消除遞迴
f = f * i;
return f;
}
Ackerman 函式定義如下:
Ackerman 函式相應演算法如下:
public static long Ack(long m,long n)
//Ackerman 遞迴演算法實現
{
if(m == 0)
return n + 1;
else if(n==0)
return Ack(m - 1, 1);
else
return Ack(m - 1, Ack(m, n - 1));
}
2. 遞迴呼叫過程
遞迴問題可以分解成規模小且性質相同的問題加以解決。下面我們以著=名的漢諾塔問題為例來說明遞迴的呼叫過程。
n 階漢諾塔問題。假設有3 個塔座X 、Y 、Z ,在塔座X 上放置n 個直徑大小各不相同、從小到大編號為1 ,2 ,… ,n 的圓盤,如圖3-9 所示。要求將X 軸上的n 個圓盤移動到塔座Z 上並要求按照同樣的疊放順序排列,圓盤移動時必須遵循以下規則:
(1 )每次只能移動一個圓盤。
(2 )圓盤可以放置在X 、Y 和Z 中的任何一個塔座。
(3 )任何時候都不能將一個較大的圓盤放在較小的圓盤上。
如何實現將放在X 上的圓盤按照規則移動到Z 上呢?當n=1 時,問題比較簡單,直接將編號為1 的圓盤從塔座X 移動到Z 上即可。當n>1 時,需要利用塔座Y 作為輔助塔座,若能將放置在編號為n 上的n -1 個圓盤從塔座X 上移動到Y 上,則可以先將編號為n 的圓盤從塔座X 移動到Z 上,然後將塔座Y 上的n -1 個圓盤移動到塔座Z 上。而如何將n -1 個圓盤從一個塔座移動到另一個塔座又成為與原問題類似的問題,只是規模減小了1 ,因此可以用同樣的方法解決。這是一個遞迴問題,漢諾塔的演算法描述如下:
public static void Hanoi(int n,String A,String B,String C)
// 將塔座A 上從小到大自上而下編號為1 到n 的圓盤按照規則搬到塔座C 上,B 可以作為輔助塔座
{
if(n == 1)
move(1, A, C); //
將編號為1
的圓盤從A
移動到C
else {
Hanoi(n - 1, A, C, B); //
將編號為1
到n-1
的圓盤從A
移動到B
,C
作為輔助塔座
move(n, A, C); //
將編號為n
的圓盤從A
移動到C
Hanoi(n - 1, B, A, C); //
將編號為1
到n-1
的圓盤從B
移動到C
,A
作為輔助塔座
}
}
public static void move (int n, String tempA, String tempB) {
System.out.println("move plate"+n+" from column "+tempA+" to column "+ tempB);
}
下面以n=3 為例,來說明漢諾塔的遞迴呼叫過程,如圖3-10 所示。當n>1 時,需要3 個過程移動圓盤。
第1 個過程,將編號為1 和2 的圓盤從塔座X 移動到 塔座Y 。
第2 個過程,將編號為3 的圓盤從塔座X 移動到 塔座Z 。
第3 個過程,將編號為1 和2 的圓盤從塔座Y 移動到 塔座Z 。
第1 個過程,透過呼叫Hanoi(2,X,Z,Y) 來實現。Hanoi(2,X,Z,Y) 又呼叫自己,完成將編號為1 的圓盤從塔座X 移動到 塔座Z ,如圖3-11 所示。編號為2 的圓盤從塔座X 移動到 塔座Y ,編號為1 的圓盤從塔座Z 移動到 塔座Y ,如圖3-12 所示。
圖3-11 將編號為1 的圓盤從塔座X 移動到 塔座Z
圖3-12 將編號為2 的圓盤從塔座X 移動到 塔座Y ,編號為1 的圓盤從塔座Z 移動到 塔座Y
第2 個過程完成將編號為3 的圓盤從塔座X 移動到 塔座Z ,如圖3-13 所示。
第3 個過程透過呼叫Hanoi(2,Y,X,Z) 來實現圓盤移動。透過再次遞迴完成將編號為1 的圓盤從塔座Y 移動到 塔座X ,如圖3-14 所示。將編號為2 的圓盤從塔座Y 移動到 塔座Z ,將編號為1 的圓盤從塔座X 移動到 塔座Z ,如圖3-15 所示。
本文節選自《圖解Java資料結構與演算法(微課影片版)》。
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/18841117/viewspace-2997292/,如需轉載,請註明出處,否則將追究法律責任。
相關文章
- Java遞迴演算法的使用Java遞迴演算法
- 二十一、氣泡排序演算法——JAVA實現(遞迴與非遞迴)排序演算法Java遞迴
- 遞迴演算法遞迴演算法
- 二十、快速排序演算法——JAVA實現(遞迴)排序演算法Java遞迴
- 演算法小專欄:遞迴與尾遞迴演算法遞迴
- 【演算法】遞迴演算法演算法遞迴
- 遞迴演算法要素遞迴演算法
- 解讀:什麼是Java的遞迴演算法?Java遞迴演算法
- 快速排序(遞迴及非遞迴演算法原始碼)排序遞迴演算法原始碼
- Java方法06:遞迴Java遞迴
- 演算法初探--遞迴演算法演算法遞迴
- 揹包問題的遞迴與非遞迴演算法遞迴演算法
- Java資料結構與演算法--遞迴和回溯Java資料結構演算法遞迴
- JavaScript演算法之遞迴JavaScript演算法遞迴
- 淺談遞迴演算法遞迴演算法
- 每日一演算法:遞迴演算法遞迴
- Java - 13 方法的遞迴Java遞迴
- Python進階-演算法-遞迴Python演算法遞迴
- 遞迴 & 分治演算法深度理解遞迴演算法
- 演算法分析__遞迴跟蹤演算法遞迴
- Python遞迴演算法詳解Python遞迴演算法
- 【Java資料結構與演算法筆記(二)】樹的四種遍歷方式(遞迴&非遞迴)Java資料結構演算法筆記遞迴
- 遞迴和尾遞迴遞迴
- 【電腦科學】演算法——遞迴演算法遞迴
- 遞迴與分治演算法練習遞迴演算法
- 二叉樹——後序遍歷的遞迴與非遞迴演算法二叉樹遞迴演算法
- 快速排序【遞迴】【非遞迴】排序遞迴
- java-遞迴(檔案查詢)Java遞迴
- java常見遞迴練習題Java遞迴
- iOS 演算法之排序、查詢、遞迴iOS演算法排序遞迴
- 資料結構和演算法:遞迴資料結構演算法遞迴
- 資料結構與演算法:遞迴資料結構演算法遞迴
- 10.遞迴演算法最佳解析遞迴演算法
- 五大演算法程式碼模板(DFS 遞迴非遞迴都算上,是六個)演算法遞迴
- 資料結構與演算法(十一)——演算法-遞迴資料結構演算法遞迴
- 遞迴遞迴
- Java不用遞迴的迭代快速排序示例Java遞迴排序
- Java實現多級選單(遞迴)Java遞迴