void hanoi(char src, char mid, char dst, int n)
将n个盘子从柱子src移动到柱子dst,其中可以借助柱子mid(middle 中间件)
/** * In the classic problem of the Towers of Hanoi, you have 3 rods and N disks of different * sizes which can slide onto any tower. The puzzle starts with disks sorted in ascending * order of size from top to bottom. You have the following constraints: * (A) Only one disk can be moved at a time * (B) A disk is slid off the top of one rod onto the next rod * (C) A disk can only be placed on top of a larger disk * Write a program to move the disks from the first rod to the last using stacks */ #include <stdio.h> #include <stdlib.h> /** * 递归代码 * * T = O(2^n - 1) 可推导证明 * * */ void hanoi(char src, char mid, char dst, int n) { if (n == 1) { printf("Move disk %d from %c to %c\n", n, src, dst); } else { hanoi(src, dst, mid, n - 1); printf("Move disk %d from %c to %c\n", n, src, dst); hanoi(mid, src, dst, n - 1); } } int main(void) { int n; while (scanf("%d", &n) != EOF) { hanoi('A', 'B', 'C', n); } return 0; }
题目描述: 约19世纪末,在欧州的商店中出售一种智力玩具,在一块铜板上有三根杆,最左边的杆上自上而下、由小到大顺序串着由64个圆盘构成的塔。目的是将最左边杆上的盘全部移到右边的杆上,条件是一次只能移动一个盘,且不允许大盘放在小盘的上面。现在我们改变游戏的玩法,不允许直接从最左(右)边移到最右(左)边(每次移动一定是移到中间杆或从中间移出),也不允许大盘放到下盘的上面。Daisy已经做过原来的汉诺塔问题和汉诺塔II,但碰到这个问题时,她想了很久都不能解决,现在请你帮助她。现在有N个圆盘,她至少多少次移动才能把这些圆盘从最左边移到最右边? 输入: 包含多组数据,每次输入一个N值(1<=N=35)。 输出: 对于每组数据,输出移动最小的次数。 样例输入: 1 3 12 样例输出: 2 26 531440
首先,我们分析一下这种汉诺塔变形有几种状态变化(src, bri, dst)来表示:
void move(char src, char dst, int n)
void send(char src, char dst, int num) { // src先移动到bri, bri再移动到dst }
#include <stdio.h> #include <stdlib.h> long int count; void send(char src, char dst, int num) { printf("Move %d disk from %c to %c!\n", num, src, dst); count += 1; } void move(char src, char dst, int n) { if (n == 1) { send(src, 'B', n); send('B', dst, n); } else { move(src, dst, n - 1); send(src, 'B', n); move(dst, src, n - 1); send('B', dst, n); move(src, dst, n - 1); } } int main(void) { int n; while (scanf("%d", &n) != EOF) { count = 0; move('A', 'C', n); printf("%ld\n", count); } return 0; }