通過漢諾塔深入理解遞迴流程。

2021-08-16 20:53:28 字數 1786 閱讀 6235

苦於複試的遞迴dfs問題,久久不得求解。最終決定重新來一遍大一的流程,重新了解學習遞迴。

目錄

**實現

在印度,有這麼乙個古老的傳說:在世界中心貝拿勒斯(在印度北部)的聖廟裡,一塊黃銅板上插著三根寶石針。印度教的主神梵天在創造世界的時候,在其中一根針上從下到上地穿好了由大到小的64片金片,這就是所謂的漢諾塔。不論白天黑夜,總有乙個僧侶在按照下面的法則移動這些金片,1. 一次只移動一片; 2. 不管在哪根針上,小片必在大片上面。當所有的金片都從梵天穿好的那根針上移到另外一概針上時,世界就將在一聲霹靂中消滅,梵塔、廟宇和眾生都將同歸於盡。

我們來看下三層漢諾塔模型**。

我們先給盤子編號,從上到下分別是1~n,盤子越大,編碼越大。

我們首先假設要把n個金片從寶針『a』移動寶針『b』,還有有另外一根』v』可以借用。

如果n = 1,那麼直接從 a->b 即可。

如果n = 2,那麼先把a最上面(第乙個)金片移動到v,暫且放一下,然後第二個金片移動到b目的地,接著再把v上面的移動到b目的地,所以移動的次序是 a->v, a->b, v-b。

如果n = 3,可以這麼考慮: 先不看出發地a最下面乙個最大的金片,先解決怎麼把上面兩個移走,方法我們已經知道了,但是移到**呢?只有b, v可選,b肯定是不行,因為b是目的地,那麼只能是通過b先把兩個金片移動到v(a->b, a->v, b->v),然後最下面那個最大的金片移動到目的地b(a->b)。注意這時b上面僅有這個最大的金片,a上面空的,v上面有兩個金片。接著把v上面兩個金片借由a移動到b(v->a, v->b, a->b)。這個的具體步驟,我們可以看動態圖。

如果n = 4, 同樣的不考慮最大的乙個,先把前三個移動到v,使用上面介紹的移動次序。

以此類推(其實 n = 2時,也可以看作是先解決最上面乙個的問題,然後才是把最下面的金片移動到目的地)

通過分析,發現解決n個金片的方法是先借由b,把n-1個移動到v,然後把a最下面乙個移動到b,在然後藉由a把v上面n-1移動到b。

綜上所述,我們得到了三個核心步驟。

知乎上有大神曾經說遞迴有時候更像去查字典,我們一開始想要知道這句話什麼意思,裡面有詞語不認識,查字典,字典的解釋又有新的我們不認識的詞語,然後一直查詢,直到我們弄懂了,我們開始回去理解上一層詞語的意思,不斷往上,直到最後我們理解了最初的那句話的意思。

#include

#include

#include

using

namespace

std;

void solve(int n,char src,char dst,char temp)

solve(n-1,src,temp,dst);//將n-1塊盤從src盤移動到temp盤,依靠dst做中介

cout

"/將最大的盤從目標盤移動到dst盤

solve(n-1,temp,dst,src);//將temp上的一坨盤移動到目標盤即可

}int main()

對遞迴的理解,最好的方法就是放棄一部分理解,只考慮當下,比如我們要處理規模為n的問題的時候,完全把n-1的規模當成已解決的問題去看待會好很多。放棄理解全域性,嘗試著只去理解一部分。

漢諾塔 遞迴

個人理解遞迴函式的基本要求就是,函式中呼叫函式本身,滿足特定的條件後返回。include include include include include include include include include include include include include 標頭檔案引用的較多...

遞迴漢諾塔

遞迴問題 遞迴要有三個要素 1.遞迴結束條件 2.遞迴結束時的處理 3.抽取重複的邏輯,剝離外殼 重點都在這一步 漢諾塔問題 把圓盤從下面開始按大小順序重新擺放在另一根柱子上。且規定,在小圓盤上不能放大圓盤,在三根柱子之間一次只能移動乙個圓盤。首先,要搞這個編碼得要知道漢諾塔的解題思路 1.把a塔上...

遞迴 漢諾塔

漢諾塔問題。這裡順便可以求出一共需要搬運的次數。以下是漢諾塔問題的解法 class hanoi from 搬運的起點,to 搬運的目標地,middle 臨時中轉地 private static int hanoi int level,char from,char to,char middle int...