什么是递归?
简单来说递归就是一个程序调用自己本身的一种方法。就比如说你现在在看电视,电视里的人也在看电视......再比如说高中数学常见的一种分段函数
n阶Hanoi塔问题
【问题描述】
假设有 3 个分别命名为 A、B、C 的塔座,在塔座A上插有n(假设这里 n=3)个直径大小各不相同、由小到大,编号为 1,2,...,n (n=3) 的圆盘,如上图。现要求将塔座 A 上的圆盘全部移至塔座 C 上,并仍然同样的顺序叠排,圆盘移动的时候必须遵循以下规则:
- 每次只能移动一个圆盘;
- 圆盘可以插在A、B、C中的任意一个塔座上;
- 任何时候都不能将一个较大的圆盘压在较小的圆盘之上。
假设塔座 A 上最初的圆盘总数为 n 个。
(1)当 n = 1 的时候,直接将编号为 1 的圆盘从塔座 A 移至塔座 C 上;
(2)当 n > 1 (假设这里 n = 3)的时候,将执行以下三步:
① 用塔座 C 做为过渡,将塔座 A 上的 ( n - 1) 即 2 个圆盘移到塔座 B 上;(这里用到了递归!!)
② 将塔座 A 上最后一个圆盘直接移到塔座 C 上;
③ 用塔座 A 做为过渡,将塔座 B 上的 ( n - 1) 即 2 个圆盘移到塔座 C 上。(这里也用到了递归!!)
【算法描述】
1、定义move(A, n, C),意思就是,将编号为 n 的圆盘从塔座 A 移到塔座 C 上,同时定义一个初值为 0 的全局变量 m,以此来对移动进行计数:
int m = 0; void move(char A, int n, char C) { cout << ++m << ", " << n << ", " << A << ", " << C << ", " << endl; }
2、 如果 n = 1,则直接将编号为 1 的圆盘从塔座 A 移至塔座 C 上,递归结束。
否则:定义一个Hanoi函数,即 Hanoi(n, A, B, C),意思就是,将塔座A上的n个圆盘按规则移到塔座C上,塔座B作为辅助,再如上①②③所述。(!!注意这里的A, B, C是一个代表,并非一定是指A, B, C这三个圆盘)
void Hanoi(int n, char A, char B, char C) { if(n == 1) move(A, 1, C); //将编号为 1 的圆盘从塔座A移到塔座C else { Hanoi(n - 1, A, C, B); //将塔座A上编号为 1 至 n-1 的圆盘移到塔座B上(C为辅助) move(A, n, C); //将编号为 n 二栋圆盘从塔座A移到塔座C Hanoi(n - 1, B, A, C); //将塔座B上编号为 1 至 n-1 的圆盘移到塔座C上(A为辅助) } }
总体代码实现
//汉洛塔Hanoi问题
#include <stdio.h>
#include <iostream>
using namespace std;
int m = 0;
void move(char A, int n, char C)
{
cout << ++m << ", " << n << ", " << A << ", " << C <<endl;
printf("");
}
void Hanoi(int n, char A, char B, char C)
{
if(n == 1)
move(A, 1, C);
else
{
Hanoi(n - 1, A, C, B);
move(A, n, C);
Hanoi(n - 1, B, A, C);
}
}
int main()
{
Hanoi(3, 'a', 'b', 'c');
return 0;
}
运行结果如下: