如有不对,不吝赐教
进入正题:
借助堆栈以非递归(循环)方式求解汉诺塔的问题(n, a, b, c),即将N个盘子从起始柱(标记为“a”)通过借助柱(标记为“b”)移动到目标柱(标记为“c”),并保证每个移动符合汉诺塔问题的要求。
输入格式:
输入为一个正整数N,即起始柱上的盘数。
输出格式:
每个操作(移动)占一行,按柱1 -> 柱2的格式输出。
输入样例:
3
输出样例:
a -> c
a -> b
c -> b
a -> c
b -> a
b -> c
a -> c
这个题目要求我们用反常规的思维去思考汉诺塔问题,其实是对自己思维的一个锻炼,
这个题目的关键是用堆去实现函数递归中的栈调用
下面就以3个为例来分析
我们把从下到上的编号为3,2,1
以及栈的构造:
typedef struct Stack{
int num; //柱子的编号
char source; //源
char destination; //目标
char mid; //中间的柱子
struct Stack *down;
}stack;
下面我们将塔看为最底下的一个盘(即3)并上面的所有盘作为一个盘(即2和1),那么问题变为了两个盘,这个移动就很简单了。
我们先把1,2盘移动到b,再把3移动到c,最后再把1,2盘移动到c
这在栈里面的操作就是 Push 3:a->c
为了将3移动出来,我们要把1,2放到b,于是问题就变成了怎么把1,2放到b,按照上面的分发,栈中的操作就是Push 2:a->b,然后就变成了怎么把1放到c,执行Push:a->c
代码就是:
top=(stack *)malloc(sizeof(stack));
top->down=NULL;
top->source='a';
top->mid='b';
top->destination='c';
top->num=N; //初始化第一个栈节点
i=N-1;
while(i){
top=Push(i,top->source,top->destination,top->mid,top);
i--;