当只有一个圆盘时,A塔只需直接移动到C塔即可,即A->C。
当有两个圆盘时,先将A塔上面一个圆盘移到B塔,然后将A塔下面圆盘移到C塔,然后再把B塔的盘移到C塔即可。其先后顺序是这样的:A->B,A->C,B->C。
假如需要把A塔的盘移到B塔呢?
先将A塔上面一个圆盘移到C塔,然后将A塔下面圆盘移到B塔,然后再把C塔的盘移到B塔即可。其先后顺序是这样的:A->C,A->B,C->B。
规律1:显然,无论移到B塔还是C塔,其方法都是一样的,都是借助剩下的一个塔(把它叫做中介塔吧),移动A塔上面的圆盘到中介塔,然后把A塔最下面的圆盘移动至目标塔即可。
注:这里A塔为源塔,若B为中介塔,则C为目标塔,反之亦然。
根据小学一年级的知识,我们引入函数的概念
一个圆盘的情况可以这么表示:
(1)
(2)
注:这里A塔为源塔,若B为中介塔,则C为目标塔。
好,来尝试一下三个圆盘的。
想圆盘由A塔都搬到C塔,第一步,则应把上面两个圆盘都搬到B塔,第二步,把A塔最底下的圆盘搬到C塔,第三步,则应把B塔的盘都移到C塔。
显然,第一步想一下子把两个圆盘从A搬至B不太现实,我们回到规律1想了下,发现此时目标塔为B塔,而中介塔则为C塔,根据函数的概念得出它的公式为:
(3)
显然,第二步则为A->C,这是永远不变的。
规律二:在C塔为目标塔的情况下,第二步(即中间的步骤)一定为A->C。
同理,第三步代入规律1,发现此时B塔为源塔,A为中介塔,C为目标塔。得到公式:
(4)
综上所得:
(5)
来尝试一下四个圆盘的。
(6)
由公式(6)发现:
(7)
公式后面部分第一步为B,C两个字母交换,第三步为A,B两个字母交换。
分析可得,假设A盘有n个盘,把A盘以上得盘定义为n-1盘,最下面得盘定义为第n盘,步骤为:
1.先把A盘上的n-1个盘先移到B盘,中介塔为C盘
2.再把A盘的第n个盘移到C盘,中介塔为B盘
3.最后把B盘的n-1个盘移到C盘中介塔为A盘
代码实现
public class HanoiTower {
// 编写一个main方法
public static void main(String[] args) {
Tower tower = new Tower();
tower.move(3, 'A', 'B', 'C');
}
}
class Tower {
// 方法
// num表示圆盘个数,A表示A塔,B表示B塔,C表示C塔
public void move(int num, char A, char B, char C) {
// 如果只有一个圆盘
if(num == 1) {
System.out.println(A + "->" + C);
} else { // 假定有两个圆盘
// 1.先从A移动上面的盘到B,C为中介塔
move(num - 1, A, C, B);
// 2.再把A下面的盘移动至C
System.out.println(A + "->" + C);
// 3.再把B的盘移动至C,A为中介塔
move(num - 1, B, A, C);
}
}
}
代码实现的底层原理: