網站首頁 編程語言 正文
題目描述
漢諾塔問題起源于一個傳說
漢諾塔又被稱為河內塔,傳說,在世界中心貝拿勒斯(在印度北部)的圣廟里,一塊黃銅板上插著三根寶石針。
印度教的主神梵天在創造世界的時候,在其中一根針上從下到上地穿好了由大到小的64片金片,這就是所謂的漢諾塔。 不論白天黑夜,總有一個僧侶在按照下面的法則移動這些金片:一次只移動一片,不管在哪根針上,小片必須在大片上面。 僧侶們預言,當所有的金片都從梵天穿好的那根針上移到另外一根針上時,世界就將在一聲霹靂中消滅,而梵塔、廟宇和眾生也都將同歸于盡。
我們現在要研究的就是在不同情況下盤子的移動順序和移動的次數。
畫圖分析
由簡到繁,我們先從最簡單的情況來分析:
~~只有一個盤子的時候:
只有一個盤子我們直接把它從A柱移到C柱就行,此時移動次數是1,移動順序是 A->C
~~有兩個盤子的時候:
有兩個盤子的時候我們需要先將較小的盤子移動到B柱,然后將較大的盤子移動C柱,再將B柱上的盤子移動到C柱;此時移動次數是3,移動順序是 A->B A->C B->C
~~有三個盤子的時候:
有三個盤子的時侯,我們把最小的盤子命名為1,中間的為2,最大的為3,那么移動順序應該是:1號移到到C柱,2號移動到B柱,1號移動到B柱,3號移動到C柱,1號移動到A柱,2號移動到C柱,1號移動到C柱;一共移動7次,移動順序是A->C A->B C->B A->C B->A B->C A->C
A->C A->B C->B
A->C B->A
B->C A->C
思路總結
在上面的移動過程中,B柱始終起著中轉的作用,我們我們可以理解為:
- A柱:起始柱
- B柱:中轉柱
- C柱:目標柱
同時,我們發現一個盤子時需要移動一次,兩個盤子時需要移動3次,3個盤子時需要移動7次,所以總結規律:n個盤子需要移動的次數是 2n-1 次。
其次,我們可以把上面的移動過程簡化為三個步驟:
- 把n-1個盤子通過C柱移到B柱上。
- 把A柱上的最后一個盤子移動到C柱上。
- 把n-1個盤子通過A柱移動到C柱上。 ?
比如,上面盤子個數為三的時候,我們可以分解為:第一步:1號移到到C柱,2號移動到B柱,1號移動到B柱;第二步:3號移動到C柱;第三步:1號移動到A柱,2號移動到C柱,1號移動到C柱。
所以,n個盤子的移動順序為:
1、把n-1個盤子通過C柱移到B柱上。
2. 把A柱上的最后一個盤子移動到C柱上。
3. 把n-1個盤子通過A柱移動到C柱上。
代碼實現
#include<stdio.h>
//Move函數,用來移動盤子,pos1表示起始柱,pos2表示目標柱
void Move(char pos1, char pos2)
{
printf("%c->%c ", pos1, pos2); //把pos1的盤子移動到pos2
}
//Hanoi函數,用來實現漢諾塔,其中n表示盤子的個數,pos1表示起始柱,pos2表示中轉柱,pos3表示目標柱
void Hanoi(int n, char pos1, char pos2, char pos3)
{
if (1 == n) //當n==1時,直接把盤子從A柱移動到C柱
{
Move(pos1, pos3);
}
else //當n不等于1時,分三步走
{
//第一步:將n-1個盤子通過C柱移動到B柱,此時C柱時中轉柱,B柱是目標柱
Hanoi(n - 1, pos1, pos3, pos2);
//第二步:把A柱最后一個盤子直接移動到C柱
Move(pos1, pos3);
//第三步:將n-1個盤子通過A柱移動到C柱,此時B柱是起始柱,A柱是中轉柱,C柱是目標柱
Hanoi(n - 1, pos2, pos1, pos3);
}
}
int main()
{
//定義一個變量來表示盤子的個數
int n = 0;
//定義三個字符變量來表示三根柱子
char pos1 = 'A';
char pos2 = 'B';
char pos3 = 'C';
//調用hanoi函數
Hanoi(1, pos1, pos2, pos3); //n為1
printf("\n");
Hanoi(2, pos1, pos2, pos3); //n為2
printf("\n");
Hanoi(3, pos1, pos2, pos3); //n為3
printf("\n");
Hanoi(4, pos1, pos2, pos3); //n為4
printf("\n");
return 0;
}
總結
知道了漢諾塔的邏輯后,我們重新回到這個問題,我們發現,要把64片金片全部挪完需要挪動 264-1 次,假設這個僧侶一秒鐘移動一次,那么一共要挪 (264-1) / 3600 / 24 / 365 = 584,942,417,355(年),那時候地球已經毀滅也不是沒有可能,哈哈。
原文鏈接:https://blog.csdn.net/m0_62391199/article/details/124531394
相關推薦
- 2022-09-04 關于Python下的Matlab函數對應關系(Numpy)_python
- 2022-03-12 深入了解C#多線程安全_C#教程
- 2022-05-20 springCloud_Nacos服務搭建
- 2022-04-19 python使用requests?POST提交一個鍵多個值方式_python
- 2022-06-09 Python+OpenCV實現圖片中的圓形檢測_python
- 2022-06-28 一文搞懂Python中的進程,線程和協程_python
- 2023-11-18 Python list寫入txt文件
- 2022-07-04 C#使用StreamReader和StreamWriter類讀寫操作文件_C#教程
- 最近更新
-
- window11 系統安裝 yarn
- 超詳細win安裝深度學習環境2025年最新版(
- Linux 中運行的top命令 怎么退出?
- MySQL 中decimal 的用法? 存儲小
- get 、set 、toString 方法的使
- @Resource和 @Autowired注解
- Java基礎操作-- 運算符,流程控制 Flo
- 1. Int 和Integer 的區別,Jav
- spring @retryable不生效的一種
- Spring Security之認證信息的處理
- Spring Security之認證過濾器
- Spring Security概述快速入門
- Spring Security之配置體系
- 【SpringBoot】SpringCache
- Spring Security之基于方法配置權
- redisson分布式鎖中waittime的設
- maven:解決release錯誤:Artif
- restTemplate使用總結
- Spring Security之安全異常處理
- MybatisPlus優雅實現加密?
- Spring ioc容器與Bean的生命周期。
- 【探索SpringCloud】服務發現-Nac
- Spring Security之基于HttpR
- Redis 底層數據結構-簡單動態字符串(SD
- arthas操作spring被代理目標對象命令
- Spring中的單例模式應用詳解
- 聊聊消息隊列,發送消息的4種方式
- bootspring第三方資源配置管理
- GIT同步修改后的遠程分支