Hanoi(汉诺)塔问题

devtools/2024/10/19 17:44:37/

目录

什么是汉诺塔?

如何分析汉诺塔

代码实现汉诺塔


什么是汉诺塔?

这是一个古典的数学问题,是一个用递归方法解题的典型例子。汉诺塔的故事在这里不做介绍啦!

汉诺塔的思想是:

        总共有3根柱子,这里假设为A、B、C。A上有n个圆盘,圆盘的大小由下到上依次递减,现在我们要把这n个盘子借助B从A移动到C,但是每次只允许移动一个盘,且在移动的过程中在3个柱子上的盘都始终保持大盘在下,小盘在上。

如何分析汉诺塔

实质:将A上的圆盘借助B移动到C。

条件限制:(1)每次只移动一个  (2)小在上,大在下

在这里,我们选取n=3来分析。

(这里假设三个圆盘从上到下标号为123)

Step1:首先, C为辅助,B为目标。将1,2,即n - 1个圆盘移到了B柱上,C 柱为空,A 柱还剩下一个最大的盘子。

将盘子1从A -> C
将盘子2从A -> B
将盘子1从C -> B

在这一步之后,A上有3,B上有12,C为空。

Step2:将最大的盘子移动到了目标柱 C 上

将盘子3从A -> C

在这一步之后,A为空,B上有12,C有3。

两步之后,我们已经成功把3,移动到了我们想要放置的位置。

接下来用相同的方法,把2移动到C上。

Step3:此时 A 为辅助,C 为目标。将1,即n - 1个圆盘移到了A柱上,B柱还剩下一个最大的盘子。

将盘子1从B -> A

在这一步之后,A上有1,B为2,C上有3。

Step4:将当前最大的盘子移动到了目标柱 C 上

将盘子2从B -> C

在这一步之后,A上有1,B为空,C上有23。

又两步之后,我们已经成功把2,移动到了我们想要放置的位置。

Step5:此时 B为辅助,C 为目标。但此时,只剩一个盘子,我们可以直接将盘子移动到C上。

将盘子3从A -> C   

在这一步之后,A为空,B为空,C上有123。 

至此,完成了圆盘的移动。

小结:

        从上面的分析我们可以看出,空的柱子为辅助,且两个步骤为一组(可以将一个圆盘正确的移动到目标柱C上)。于此,我们可以推到n个圆盘,每次借助辅助放置n-1个盘。

        因此,不难看出,汉诺塔的问题本身是一个大问题,我们可以将这个大问题转化为许多个相似的小问题,其解决方案与将一个较小的汉诺塔移动到另一个柱子上的解决方案相似。这里我们就需要用到递归了。

代码实现汉诺塔

#include<stdio.h>int  main()
{void hanoi(int n,char disA,char disB,char disC);  //对hanoi函数进行声明int n;printf("输入一个整数n表示汉诺塔上圆盘的个数:"); scanf("%d",&n);printf("汉诺塔的移动顺序:\n");hanoi(n,'A','B','C'); return 0;} void hanoi(int n,char disA,char disB,char disC)
{void move(char x,char y);if(n==1)  //只剩一个盘子 {move(disA,disC);  //将A移动到C }else{//将disA上的前n-1个圆盘(即除了最大的那个圆盘之外的所有圆盘)移动到辅助柱子disB上//实际上是借助了disC辅助   hanoi(n-1,disA,disC,disB);   //Step1 这一步之后,disA上剩一个最大的圆盘n ,disB有n-1个 move(disA,disC);            //Step2 我们要将这个最大的圆盘n 移动到disC上 ,这一步之后,disA为空 hanoi(n-1,disB,disA,disC);  //Step3  以此递归,将空的disA作为辅助 }
}void move(char x,char y)
{printf("%c-->%c\n",x,y);
}

最后我们来总结一下,什么时候会使用到递归思想来解决问题呢?

问题可以自然地分解为与原问题相似规模更小子问题时。同时要注意递归终止的条件。

然而,需要注意的是,递归可能导致大量的函数调用和返回,如果递归深度过大,可能会导致栈溢出等问题。因此,在使用递归时,需要仔细考虑其效率和安全性。


http://www.ppmy.cn/devtools/91160.html

相关文章

MySQL笔记(十):视图

一、介绍 看一个需求 emp表里的列信息很多&#xff0c;有些信息是个人重要信息&#xff08;比如sal,comm,mgr,hiredate)&#xff0c;如果我们希望某个用户只能查询emp表的&#xff08;empno,ename,job,deptno)信息&#xff0c;有什么办法 》视图 二、视图的使用 &#xff08;1…

ios 5.5寸、ipad13英寸如何截屏

ios上架的时候&#xff0c;你可能会发现&#xff0c;上架需要ios 5.5寸&#xff0c;ipad需要13英寸的屏幕截屏。 但是尴尬了&#xff0c;我们手头上的手机&#xff0c;可能是最新的iphone 15&#xff0c;并没有远古时代iphone 8 plus的5.5寸&#xff0c;那么我们该如何截屏呢&…

【Java EE】进程和线程的区别和联系

进程和线程的区别与联系 在现代计算机科学中&#xff0c;理解进程和线程的概念对于高效编程和系统设计至关重要。进程和线程都是操作系统并发执行的基本单元&#xff0c;但它们在资源管理、执行环境、通信方式等方面存在显著区别和联系。 进程和线程的区别 1. 基本概念 进程…

【redis 第五篇章】持久化之AOF和RDB

一、概述 Redis 是内存数据库&#xff0c;如果不能将内存中的数据保存到磁盘中&#xff0c;那么一旦服务器进程退出&#xff0c;数据库中数据会消失&#xff0c;所以 Redis 提供了持久化的功能, Redis 分为两种持久化方式&#xff1a;RDB 和 AOF&#xff0c;有以下几个特点&am…

ubuntu将软件放到任务栏

右键点击这个 pycharm 方法1&#xff1a; 方法2&#xff1a; sudo nano /usr/share/applications/PyCharm.desktop 编辑这个 [Desktop Entry] NamePyCharm CommentPyCharm Integrated Development Environment Exec/path/to/PyCharm.sh Icon/path/to/PyCharm.svg Terminalf…

【LLM】-18-模型链Chains与路由链

目录 1、简单链 2、简单多链 3、顺序链&#xff08;SequentialChains&#xff09; 4、路由链&#xff08;LLMRouterChain&#xff09; 链&#xff08;Chains&#xff09;通常将大语言模型&#xff08;LLM&#xff09;与提示&#xff08;Prompt&#xff09;结合在一起&#…

TensorFlow和Pytorch是什么?干什么用的?

TensorFlow和Pytorch都是机器学习框架&#xff0c;允许用户自定义开发机器学习模型&#xff08;利用已经实现好的神经网络层&#xff09;。 1. 加载和预处理数据 加载数据&#xff1a;使用合适的库&#xff08;如 Pandas、Numpy 或 TensorFlow 的数据处理 API&#xff09;从文…

springboot项目迁移到阿里云函数

注意&#xff1a;长耗时&#xff0c;高内存 的应用&#xff0c;定时任务 不适合迁移。spring-cloud的微服务项目暂不适合迁移。 一、根据模板创建项目 1.内网数据库连接配置 如果用到了rds或者阿里云上自建的mysql数据库 则配置 internetAccess: true vpcConfig:securityGrou…