汉诺塔问题起源于印度传说,有三根柱子A、B、C,其中A柱子上有若干个大小不等的圆盘,大的在下,小的在上。目标是把所有圆盘从A柱子移动到C柱子,每次只能移动一个圆盘,并且在移动过程中不能出现大盘压小盘的情况。
解决思路:
1.当只有一个圆盘时,直接将它从A柱子移动到C柱子即可。
2.当有多个圆盘时,可以将问题分解为三个步骤:
a. 将前n-1个圆盘从A柱子经过C柱子移动到B柱子;
b. 将第n个圆盘直接从A柱子移动到C柱子;
c. 将前n-1个圆盘从B柱子经过A柱子移动到C柱子。
基于以上思路,我们可以通过递归的方式来解决汉诺塔问题。
#include <stdio.h>
void hanoi(int n, char A, char B, char C) {
if (n == 1) {
printf("Move disk 1 from %c to %c\n", A, C);
return;
}
hanoi(n - 1, A, C, B);
printf("Move disk %d from %c to %c\n", n, A, C);
hanoi(n - 1, B, A, C);
}
int main() {
int n;
printf("Enter the number of disks: ");
scanf("%d", &n);
hanoi(n, 'A', 'B', 'C');
return 0;
}
运行结果如下:
分析过程:
假设有3个圆盘,那么函数调用hanoi(3, 'A', 'B', 'C')
会执行以下步骤:
- hanoi(2, 'A', 'C', 'B') // 将2个圆盘从A经过C移动到B
- Move disk 3 from A to C // 直接将第3个圆盘从A移动到C
- hanoi(2, 'B', 'A', 'C') // 将2个圆盘从B经过A移动到C
对于hanoi(2, 'A', 'C', 'B')
,同样会执行以下步骤:
- Move disk 1 from A to B // 直接将第1个圆盘从A移动到B
- Move disk 2 from A to C // 直接将第2个圆盘从A移动到C
- Move disk 1 from B to C // 直接将第1个圆盘从B移动到C
通过递归,我们可以不断地将问题分解为更小的子问题,直到问题简化到只有一个圆盘时,直接移动即可。最终,我们得到了完整的汉诺塔问题的解决方案。