1. 程式人生 > >遞歸算法之漢諾塔

遞歸算法之漢諾塔

遞歸算法 println top 出口 rom 一個 解決問題 ati 表示

遞歸定義:

遞歸算法是把問題轉化為規模縮小了的同類問題的子問題。然後 遞歸調用函數(或過程)來表示問題的解。

一個過程(或函數)直接或間接調用自己本身,這種過程(或函數)叫遞歸過程(或函數).

遞歸算法解決問題的特點:

(1) 遞歸就是在過程或函數裏調用自身。

(2) 在使用遞歸策略時,必須有一個明確的遞歸結束條件,稱為遞歸出口。

(3) 遞歸算法解題通常顯得很簡潔,但遞歸算法解題的運行效率較低。所以一般不提倡用遞歸算法設計程序。

(4) 在 遞歸調用的過程當中系統為每一層的返回點、局部量等開辟了棧來存儲。遞歸次數過多容易造成 棧溢出等。所以一般不提倡用遞歸算法設計程序。

例子:漢諾塔

技術分享圖片

解:(1)n == 1

      第1次 1號盤 A---->C sum = 1 次

(2) n == 2

      第1次 1號盤 A---->B

       第2次 2號盤 A---->C

      第3次 1號盤 B---->C sum = 3 次

  (3)n == 3

        第1次 1號盤 A---->C

        第2次 2號盤 A---->B

        第3次 1號盤 C---->B

        第4次 3號盤 A---->C

        第5次 1號盤 B---->A

        第6次 2號盤 B---->C

        第7次 1號盤 A---->C sum = 7 次

不難發現規律:1個圓盤的次數 2的1次方減1

       2個圓盤的次數 2的2次方減1

3個圓盤的次數 2的3次方減1

。 。 。 。 。

n個圓盤的次數 2的n次方減1

故:移動次數為:2^n - 1

代碼實現:

// topN盤子個數,from-->初始塔座 inter-->輔助塔座 to-->最終塔座
    public static void doTower(int topN, char from, char inter, char to) {
        if (topN == 1) {
            System.out.println("盤子1,從" + from + "塔座 到" + to + "塔座");
        } else {
            doTower(topN - 1, from, to, inter);
            System.out.println("盤子" + topN + ",從" + from + "塔座 到" + to + "塔座");
            doTower(topN - 1, inter, from, to);
        }
    }

遞歸算法之漢諾塔