汉诺塔问题
关于汉诺塔游戏的规则就不赘述了,这里简单解释一下如何去解决汉诺塔问题。
问题的核心是如何将最大的一块移动到目标位置,约定一下,开始生成的位置是src,中间位置为mid,目标为dest,以4块为例,从大到小编号为1、2、3、4。那么如何将最大的一块移过去呢?
要想最大的一块移到dest,则必须有,最大的一块上没有其他圆盘,目标位置上没有其他圆盘,则其他圆盘都必须在mid上的位置,根据游戏规则他们是按照从大到小的顺序排列上去的。如下图所示:
现在将最大的一块移过去,那么以后最大的一块就可以不动了,现在问题的规模变小了,有3块圆盘,如何从mid移到dest?
现在已经不需要考虑1号圆盘了,即可以认为1号圆盘已经不存在了,只要考虑4、3、2即可。和上面的分析同理,将3、4移到中转的位置src,然后可以将2号移动到dest。
通过一步步的分解,我们最终可以得到只需要移动一次的操作,此时开始进行移动。总得来说:1->2->3->4,即要解决1,就要解决2;要解决2,就要解决3;要解决3,就要解决4。而4是很好解决的,因此我们解决了4->3->2->1,即4被解决了,那么3也被解决了,3被解决了2也被解决了,2被解决了1也解决了,从而整个问题就解决了。
下面附上C++代码
#include "iostream"
using namespace std;
int b, m = 0;
void Hanoi(int n, char src, char mid, char dest);
int main() {
while (true)
{
cin >> b;
Hanoi(b, 's', 'm', 'd');
cout << "step number is" << m<<endl;
m = 0;
}
}
void Hanoi(int n,char src,char mid,char dest){
if (n == 1)
{//当只要移动一次的时候,这个问题可以直接解决
cout << src << "->" << dest <<endl;
m++;//移动次数+1
return;
}
Hanoi(n - 1, src, dest, mid);//将上面的n-1个圆盘移动到中转位置
cout << src << "->" << dest << endl;//将最下面的移到目标位置
m++;//移动次数+1
Hanoi(n - 1, mid, src, dest);//将剩下的n-1个移动到目标位置
return;
}