递归典型例题:汉诺塔问题

news2024/10/7 9:16:34

文章目录

  • 1. 什么是汉诺塔
  • 2. 汉诺塔的解题步骤
  • 3. 代码实现汉诺塔

1. 什么是汉诺塔

1. 汉诺塔的来源

一位法国数学家曾编写过一个印度的古老传说:在世界中心拿勒斯的圣庙里边,有一块黄铜板,上边插着三根宝柱。印度教的主神梵天在创造世界的时候,在其中一根柱从下到上穿好了 64 片金片,这就是所谓的汉诺塔。然后不论白天黑夜,总有一名僧侣按照下面的法则来移动这些金片:一次只移动一片,不管在哪根柱子上,小片必须在大片上面。

2. 汉诺塔的玩法

  • 暂时用三层的汉诺塔来演示,初始状态下的汉诺塔如下图所示:

在这里插入图片描述

  1. step1 X → Z,如下图所示。

在这里插入图片描述

  1. step2 X → Y,如下图所示。

在这里插入图片描述

  1. step3 Z → Y,如下图所示。

在这里插入图片描述

  1. step4 X → Z,如下图所示。

在这里插入图片描述

  1. step5 Y → X,如下图所示。

在这里插入图片描述

  1. step6 Y → Z,如下图所示。

在这里插入图片描述

  1. step7 X → Z,如下图所示。

在这里插入图片描述

2. 汉诺塔的解题步骤

对于上述游戏的玩法,可以简单分解为以下三个步骤

  1. 将前 n-1 个盘子从 X 柱移动到 Y 柱上,,确保大盘在小盘下面。
  2. 将最下面的第 n 个盘子从 X 柱移动到 Z 柱上。
  3. 将 Y 柱上的 n-1 个盘子移动到 Z 柱上。
  • 在游戏中,由于每次只能移动一个圆盘,所以在移动的过程中显然要借助另外一根柱子才可以实施。
    • 步骤(1)将 X 柱上的 1 ~ n-1 个盘子移动到 Y 柱上,需要借助 Z 柱;
    • 步骤(3)将 Y 柱上的 n-1 个盘子移动到 Z 柱上,则需要借助 X 柱。
  • 所以把新的思路分成以下两个问题。
    • 问题1:如何将 X 柱上的 n-1 个盘子借助 Z 柱移动到 Y 柱上?
    • 问题2:如何将 Y 柱上的 n-1 个盘子借助 X 柱移动到 Z 柱上?
  • 解决这两个问题的方法与解决 “ 如何将 X 柱上的 n 个盘子借助 Y 柱移动到 Z 柱上?” 这个问题是一样的,都是可以拆解成上述三个步骤来实现。

问题1:将(如何将 X 柱上的 n-1 个盘子借助 Z 柱移动到 Y 柱上?)这个问题拆解为:

  1. 将前 1 ~ n-2 个盘子从 X 柱移动到 Z 柱上,确保大盘在小盘下面。
  2. 将最底下的第 n-1 这一个盘子移动到 Y 柱上。
  3. 将 Z 柱上的 1 ~ n-2 个盘子移动到 Y 柱上。

问题2:将(如何将 Y 柱上的 1 ~ n-1 个盘子借助 X 柱移动到 Z 柱上?)这个问题拆解为:

  1. 将前 1 ~ n-2 个盘子从 Y 柱移动到 Z 柱上,确保大盘在小盘下面。
  2. 将最底下的第 n-1 这一个盘子移动到 Z 柱上。
  3. 将 X 柱上的 1 ~ n-2 个盘子移动到 Y 柱上。

3. 代码实现汉诺塔

  • 汉诺塔的拆解过程刚好就满足递归算法的定义,因此,使用递归来解决汉诺塔问题就变得很简单了。
#include <stdio.h>

int count = 0;

void hanoi(int n, char x, char y, char z)
{
	if (1 == n)//如果只有一层则直接将盘子从 X 移到 Z 柱即可
	{
		printf("%c --> %c\n", x, z);
	}
	else//反之则看着解题步骤去写代码
	{
		hanoi(n - 1, x, z, y);//步骤1:将前 n-1 个盘子借助 z 柱从 x 柱移到 y 柱
		printf("%c --> %c\n", x, z);
		hanoi(n - 1, y, x, z);//步骤3:将 Y 柱上的 n - 1 个盘子借助 x 柱移动到 z
	}
	count++;
}
int main()
{
	int n;

	printf("请输入汉诺塔的层数:");
	scanf("%d", &n);

	hanoi(n, 'X', 'Y', 'Z');//n:汉诺塔层数。X Y Z:汉诺塔的三根柱子
	printf("一共移动了%d步\n", count);

	return 0;
}

在这里插入图片描述

代码分析

在这里插入图片描述

  • 想要解决一个 3 层的汉诺塔,就得先解决两个 2 层的汉诺塔,要完成一个 2 层的汉诺塔又得先完成两个 1 层的汉诺塔。
  • 同理,想要解决一个 n 层的汉诺塔,就得先解决两个 n-1 层的汉诺塔,解决一个 n-1 层的汉诺塔就又得先完成两个 n-2 层的汉诺塔。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/726857.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

div绑定键盘点击事件

为箭头绑定绑定键盘方向键 <div class"toggle-nav"><spanv-if"leftToggleSt"click"toggleGoods(1)"keyup.left"toggleGoods(1)"class"toggle-left"><a-icon type"left" class"icon" /&…

Linux系统设置

Linux的系统设置 01 选择“Install CentOS7” 02 选择安装界面的语言 03 选择时区&#xff0c;这里选择上海 04 选择安装类型&#xff0c;选择最小安装即可&#xff0c;不需要图形界面与其他的组件 05 选择安装位置&#xff0c;自定义分区 06 我要配置分区&#xff0c;进行…

ARS408毫米波雷达使用记录

参考&#xff1a;ARS_408毫米波雷达数据解析学习记录 感谢博主的分享&#xff08;https://blog.csdn.net/weixin_49401384&#xff09; 雷达can消息解析&#xff08;通用can解析思路&#xff09; socketcan学习can总线 毫米波雷达can协议解读RadarCfgRadarState 代码基本是关于…

Python接口自动化核心模块 - 数据库操作和日志

进行接口测试时&#xff0c;我们需要连接到数据库中&#xff0c;对数据源进行备份、还原、验证等操作。 Python连接数据库常见模块 MysqlDB python2时代最火的驱动库。基于C开发&#xff0c;对windows平台不友好。现在已经进入python3时代&#xff0c;基本不再使用 MysqlCl…

干农活太累了,尤其是对一位22女孩来说

干农活太累了&#xff0c;尤其是对一位22女孩来说。要是能够通过电商来销售农产品可以大大减轻干农活的负担。在重庆荣昌的一个小村庄里&#xff0c;一个名叫杨儿杨的00后女孩&#xff0c;正通过抖音电商&#xff0c;书写着她自己的故事。杨儿杨的生活并不容易。5岁前&#xff…

数据库 --- mysql(01)

MYSQL 1、数据库简介 数据&#xff1a;描述事物的符号记录&#xff0c; 可以是数字、 文字、图形、图像、声音、语言等&#xff0c;数据有多种形式&#xff0c;它们都可以经过数字化后存入计算机。 数据库&#xff1a;存储数据的仓库&#xff0c;是长期存放在计算机内、有组…

武大+上交提出 BatGPT:创新性采用双向自回归架构,可预测前后token

进NLP群—>加入NLP交流群 本论文介绍了一种名为BATGPT的大规模语言模型&#xff0c;由武汉大学和上海交通大学联合开发和训练。 该模型采用双向自回归架构&#xff0c;通过创新的参数扩展方法和强化学习方法来提高模型的对齐性能&#xff0c;从而更有效地捕捉自然语言的复杂…

Seata 分布式事务的中间件Seata设计和实现方案

文章目录 分布式事务的中间件SeataSeata AT 模式-默认模式前提整体机制写隔离读隔离 Seata XA 模式前提整体机制工作机制 Seata TCC 模式Seata Saga 模式概述缺点&#xff1a; Saga的实现外传 分布式事务的中间件Seata Seata 是一款开源的分布式事务解决方案&#xff0c;致力于…

element ui组件的自定义类名样式不生效

element ui中&#xff0c;类似描述列表这种组件 会提供自定义类名属性 需要注意&#xff0c;样式不能写在<style scoped>标签中&#xff0c;会被vue自动加上data-v属性&#xff0c;导致样式失效。 必须写在<style>标签里

C++进阶—红黑树详解及map、set封装(3)

目录 1. 红黑树的概念 2. 红黑树的性质 3. 红黑树节点的定义 4. 红黑树性质分析 5. 红黑树插入节点简要分析&#xff08;新插入节点的parent为红色&#xff09; 5.1 简要分析1-变色&#xff1a; 5.2 简要分析2-变色旋转 5.3 简要分析总结 6. 红黑树插入节点详细分析 …

Linux下载安装Redis(Ubuntu系统)

相比于 Windows 系统而言&#xff0c;Redis 更适合于在 Linux 系统上使用&#xff0c;这是由 Redis 的底层机制决定的。下面介绍一下如何在 Linux 发行版 Ubuntu 系统上安装 Redis 数据库。 了解Redis版本 Redis 版本号采用国际标准惯例&#xff0c;即“主版本号.副版本号.补…

Linux分布式应用 Zabbix监控软件 安装

zabbix 是什么&#xff1f; ●zabbix 是一个基于 Web 界面的提供分布式系统监视以及网络监视功能的企业级的开源解决方案。 ●zabbix 能监视各种网络参数&#xff0c;保证服务器系统的安全运营&#xff1b;并提供灵活的通知机制以让系统管理员快速定位/解决存在的各种问题。 ●…

第七届御网杯re的wp_Ba0

re拿了一血和二血&#xff0c;感觉挺简单的&#xff08; 1、easycpp 使用IDA进行linux动调 主要异或加密&#xff0c;还原即可 1 2 3 4 flag1[0x23,0x21,0x27,0x22,0x27,0x27,0x25,0x2B,0x2D,0x26,0x23,0x23,0x22,0x26,0x27,0x2E] flag[18,19,20,22,18,17,18,19,20,22,18,17…

visual stodio 编译

一、生成文件复制一份到其他路径 选到这里&#xff0c;添加命令&#xff1a; PlatformName 平台版本 x86/x64 Configuration 配置生成目录 Debug/Release OutputPath 生成路径 Debug/Release copy /y "$(OutputPath)$(ProjectName).dll" "E:\Project\UseDll…

LED点阵动画

23-7-6 #include<regx52.h> #include "Delay.h" #include "Matrix.h" /*点阵屏显示动画*/ unsigned char code Animation[]{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xff,0x08,0x08,0x08,0xff,0x00,0x0e,0x15,0x15,0x15,0x08,0x00,0x7e,0x01,0x02,…

用户数据报协议 UDP

文章目录 一、UDP数据报格式二、UDP校验和计算1.伪报头2.伪报头结构3.检验和计算 三、UDP特点 UDP 的特点&#xff1a; 无连接、不可靠&#xff0c;运行快捷&#xff1a; 在传输报文之前不需要建立连接&#xff0c;因此减少了协议开销与传输延时。此外&#xff0c;除了对报文提…

2023年湖北成人高考学习全流,今天启程别详细给大家介绍!

2023年湖北成人高考学习全流&#xff0c;今天启程别详细给大家介绍&#xff01; 成人高考可以准备起来了&#xff0c;那么你了解成人高考的学习流程吗&#xff1f; 一、考前准备 确认好报考条件&#xff0c;准备报名资料&#xff0c;拿到书本教材开始复习备考。 湖北成人高考报…

canvas 绘制包含10个换行(‘\n’)文字例子,要求可以设置行高,文字最后整体在canvas的高度垂直居中

canvas 绘制包含10个换行(‘\n’)文字例子,要求可以设置行高,文字最后整体在canvas的高度垂直居中。 <!DOCTYPE html> <html lang"en"> <head><meta charset"UTF-8"><title>Canvas Text Example</title><style>…

Redis锁防止重复提交

1.自定义注解方式 /*** author &#xff1a;网寻星公众号* date &#xff1a;Created in 2023/5/30 10:58* description&#xff1a;Redis锁防止重复提交* modified By&#xff1a;* version: 1.0$*/ Target({ElementType.METHOD}) Retention(RetentionPolicy.RUNTIME) Docume…

好用的记事本app怎么切换字体颜色呢?

很多人在使用记事本app的时候&#xff0c;会记录多条不同的内容&#xff0c;为了突出某条内容的重要性&#xff0c;将它的字体切换成更醒目的颜色是很多人都在使用的办法。对于比较好用的记事本软件来说&#xff0c;怎样操作才能切换字体颜色呢&#xff1f;以iPhone手机端敬业签…