递归—汉诺塔
漢諾塔是經典遞歸問題:相傳在古印度圣廟中,有一種被稱為漢諾塔(Hanoi)的游戲。該游戲是在一塊銅板裝置上,有三根桿(編號A、B、C),在A桿自下而上、由大到小按順序放置64個金盤(如下圖)。游戲的目標:把A桿上的金盤全部移到C桿上,并仍保持原有順序疊好。操作規則:每次只能移動一個盤子,并且在移動過程中三根桿上都始終保持大盤在下,小盤在上,操作過程中盤子可以置于A、B、C任一桿上。
1:如果A只有一個(A->C)
2:如果A有兩個(A->B),(A->C),(B->C)
3:如果A有三個(A->C),(A->B),(C->B),(A->C),(B->A),(B->C),(A->C).
可以發現每增加一步,其中的步驟會多很多。但是不妨這樣想。當有N個要從A->C時,且已知移動方式。使用函數表示move(a->c)。如果要是N 1個該如何想呢。是不是先不看最底下的那個盤子呢,把剩下的N從A移到B上。突然發現最底下還有一個盤子,剛好C為空,把這個最大的放在C上,剩下的就是N個從B移到C的問題了。
再看上面的3:把最上面的盤子從A移到B,在把A 的最大移到C。再把2個盤子從B借助A移到C。
再看上面的2:把最上面的盤子移到B,把最底下移到C,就轉化成B移到C一個盤子的問題了。這種遞歸要從每一步的關系找。把N個問題差成N-1移動和最底下移動的問題。
可以發現每增加一步,其中的步驟會多很多。但是不妨這樣想:
- 當有1個要從A->C時,且已知移動方式。使用函數表示move(a->c)。同理其他move操作。
- -------省略中間若干步驟不看,用遞歸思想看問題
分析:n個從a—>c和n-1個a—>c有什么聯系?(hannuo(n)—>hannuo(n-1)有啥關系)
假設有n個盤子
- hannuo(n-1)之后n-1個盤子從A—>C.
- 此時剩下底下最大的,只能移動到B,move(A,B)
- 那么你是否發現什么眉目了,只需原先的huannuo(n-1)相同操作從C—>B即可完成轉移到B;那么我們的之前函數應該寫成hannuo(n-1,A,C)但是又用到B,所以把B傳進來hannuo(n-1,A,B,C)先表示為從n-1個從A(借助B執行若干操作)轉到C。
- 這一系列操作使得將n個盤子從A—>B但是我們要的是A—>C才是需要的hannuo(n,A,B,C);那么我們只需要更改下hannuo(n-1,----)順序就好啦!
代碼如下:
package 遞歸; public class hannuota {static void move(char a,char b){System.out.println("移動最上層的"+ a+ "到"+ b+ "\t");}static void hannuota(int n,char a,char b,char c)//主要分析每一大步對于下一步需要走的。{if(n==1) {move(a,c);}//從a移到celse{hannuota(n-1,a,c,b);//將n-1個從a借助c移到bmove(a,c); //將第n(最后一個)從a移到c。hannuota(n-1,b,a,c);//再將n-1個從b借助a移到c}}public static void main(String[] args){hannuota(5,'a','b','c');} }總結
- 上一篇: 简单的五子棋操作用两种方法实现
- 下一篇: 使用eclipse自带制作帮助系统