关于汉诺塔的一个程序(关键词-#include)

关于汉诺塔的一个程序,我不理解它到底是怎么样通过递归实现的,两层还可以理解,后面就难以理解了。

#include<stdio.h>
void hanoi(int n,char x,char y,char z);
void hanoi(int n,char x,char y,char z)
{
    if(n == 1)
    {
        printf("%c-->%c\n",x,z);
    }
    else
    {
        hanoi(n-1,x,z,y);
        printf("%c-->%c\n",x,z);
        hanoi(n-1,y,x,z);
    }
}
int main(void)
{
    int n;
    printf("请输入汉诺塔层数:");
    scanf("%d",&n);
    hanoi(n,'x','y','z');
    
    return 0; 
}

假设是3层,那么你的函数运行如下:
初始,3个盘子放在柱子A上,目标是全部移动到C上
调用 hanoi(3, 'A', 'B', 'C'):
n不等于1,进入else
调用hanoi(2, 'A', 'C', 'B'):
n不等于1,进入else
调用hanoi(1, 'A', 'B', 'C'):
n等于1,进入if,打印输出:A-->C
输出:A-->B
调用hanoi(1, 'C', 'A', 'B')
n等于1,进入if语句打印输出:C-->B
递归结束
输出:A-->C
调用hanoi(2, 'B', 'A', 'C'):
n不等于1,进入else
调用hanoi(1, 'B', 'C', 'A'):
n等于1,进入if语句块,输出:B-->A
输出:B-->C
调用hanoi(1, 'A', 'B', 'C'):
n等于1,进入if,输出:A-->C
递归结束
输出:B-->C

  • 帮你找了个相似的问题, 你可以看下: https://ask.csdn.net/questions/7446374
  • 这篇博客也不错, 你可以看下(案例复盘)用抽象数据结构解决问题【集合的交、并、补】
  • 除此之外, 这篇博客: 预处理指令中的 即#include预处理指令的作用是在指令处展开被包含的文件。 部分也许能够解决你的问题, 你可以仔细阅读以下内容或跳转源博客中阅读:
    • 包含可以是多重的,也就是说一个被包含的文件中还可以包含其他文件
    • 标准C编译器至少支持八重嵌套包含。
    • 预处理过程不检查在转换单元中是否已经包含了某个文件并阻止对它的多次包含,所以我们可以在多次包含同一个头文件时,通过给定预处理时的条件来达到不同的效果。
    • include 除了可以包含头文件,还可以包.c文件,但为了避免重复定义,最好不要包.c
  • 您还可以看一下 韦语洋(Lccee)老师的一机一码加密、被破解自动销毁随时授权回收升级系列视频课程课程中的 演示误报效果,一些被误报的特征的解除方式(重要)小节, 巩固相关知识点
  • 以下回答由chatgpt基于相关博客总结生成:

    首先,让我们来了解一下递归的概念和汉诺塔问题的规则。

    递归是一种解决问题的方法,其通过将一个大问题分解为多个相同或类似的小问题来解决。在递归过程中,每个小问题都可以通过调用相同的函数来解决。递归函数通常有一个或多个基准情况,用于结束递归的循环。

    汉诺塔问题是一个经典的数学问题。它包含三个塔和一些不同大小的圆盘,开始时,所有的圆盘都被放置在一个塔上,按照从大到小的顺序。问题的目标是将所有圆盘从起始塔移动到目标塔,同时遵循以下规则: 1. 每次只能移动一个圆盘。 2. 每次移动时,大圆盘不能放在小圆盘上。

    现在,让我们来解释一下递归如何解决汉诺塔问题。

    步骤1: 定义递归函数 我们可以定义一个递归函数,该函数接受四个参数:源塔A、辅助塔B、目标塔C和要移动的圆盘数量n。函数的目标是将n个圆盘从塔A移动到塔C,并借助辅助塔B。

    步骤2: 处理基准情况 当n等于1时,说明只有一个圆盘需要移动。在这种情况下,我们可以直接将圆盘从塔A移动到塔C,并结束递归。

    步骤3: 递归调用 当n大于1时,我们需要递归调用函数来解决更小的子问题。具体步骤如下: 1. 将n-1个圆盘从塔A移动到辅助塔B。这可以通过将n-1作为新的圆盘数量传递给递归函数来实现。 2. 将剩下的一个圆盘从塔A移动到塔C。 3. 最后,将n-1个圆盘从辅助塔B移动到目标塔C。

    通过递归调用,我们可以将整个问题分解为小问题,直到基准情况为止。然后,我们可以按照递归的方式逐步解决这些小问题,最终得到整个问题的解决方案。

    下面是一个示例代码,演示了如何使用递归函数来实现汉诺塔问题的解决方案:

    #include <iostream>
    
    void moveDisk(int n, char source, char target, char auxiliary) {
        if (n == 1) {
            // Move the disk directly from source to target
            std::cout << "Move disk 1 from " << source << " to " << target << std::endl;
            return;
        }
    
        // Move n-1 disks from source to auxiliary
        moveDisk(n - 1, source, auxiliary, target);
    
        // Move the remaining disk from source to target
        std::cout << "Move disk " << n << " from " << source << " to " << target << std::endl;
    
        // Move the n-1 disks from auxiliary to target
        moveDisk(n - 1, auxiliary, target, source);
    }
    
    int main() {
        int numDisks = 3;
        char source = 'A', target = 'C', auxiliary = 'B';
    
        moveDisk(numDisks, source, target, auxiliary);
    
        return 0;
    }
    

    这段代码使用了递归函数moveDisk来解决汉诺塔问题。在moveDisk函数中,我们首先处理了基准情况(当n==1时),然后递归调用moveDisk函数来解决较小的子问题。最终,我们得到了将n个圆盘从源塔移动到目标塔的完整解决方案。

    希望这个解释和示例代码可以帮助你更好地理解通过递归实现汉诺塔问题。如果你还有任何问题,请随时问我。