Python数据结构16:递归实现汉诺塔

1. 汉诺塔问题的定义:

有三根柱子,其中一根套着64个由小到大的黄金盘片,任务就是要把这一叠黄金盘从一根柱子搬到另一根,但有两个规则:

  • 一次只能搬1个盘子
  • 大盘子不能叠在小盘子上
Python数据结构16:递归实现汉诺塔_第1张图片

2. 解决思路

Python数据结构16:递归实现汉诺塔_第2张图片
假设1#有五个盘子
  1. 想办法把上面的4个挪到2#,剩下的最后一个最大的挪到3#
  2. 用同样的办法把2#上的4个盘子挪到3#

现在问题是,怎么把上面的4个盘子从1#挪到2#
方法是,将1#上的前3个盘子挪到3#,再将第4个挪到2#。
那怎么把3#上的3个盘子挪到2#上呢?
还是同样的,
先把3#上的前2个盘子挪到1#上,再将第3个盘子挪到2#。
同样的,先将1#上的第一个盘子挪到3#,再将第1#上的第二个盘子挪到2#。
最后将3#上的盘子挪到2#上,就把前两个盘子挪到2#上了。

这个思路的解决过程,就是在不断地减少规模,从考虑5个盘子的移动,逐渐缩小到1个盘子的移动,一个盘子的移动就是递归的结束条件。

整体的递归思路如下:
将盘片塔从开始柱,经由中间柱,移动到目标柱

  • 首先将上层N-1个盘片的盘片塔,从开始柱,经由目标柱,移动到中间柱;
  • 然后将第N个(最大的)盘片,从开始柱,移动到目标柱;
  • 最后将放置在中间柱的N-1个盘片的盘片塔,经由开始柱,移动到目标柱;

基本结束条件,也就是最小规模问题是:
1个盘片的移动问题

3. 代码

def move_tower(height, first, second, third):
    # height是盘子的个数,first是起始柱,second是中间柱,third是目标柱
    if height >= 1:  # 最小结束条件,即剩余的盘子的个数
        move_tower(height - 1, first, third, second)  # 经由目标柱挪到中间柱
        move_disk(height, first, third)  # 最大的盘子直接挪到目标柱
        move_tower(height - 1, second, first, third)  # 将中间柱的剩下的盘子,经由开始柱,挪到目标柱


def move_disk(disk, begin, end):
    print(f"Moving disk[{disk}] from {begin} to {end}")


move_tower(3, "1#", "2#", "3#")
Moving disk[1] from 1# to 3#
Moving disk[2] from 1# to 2#
Moving disk[1] from 3# to 2#
Moving disk[3] from 1# to 3#
Moving disk[1] from 2# to 1#
Moving disk[2] from 2# to 3#
Moving disk[1] from 1# to 3#

参考文献

本文的知识来源于B站视频 【慕课+课堂实录】数据结构与算法Python版-北京大学-陈斌-字幕校对-【完结!】,是对陈斌老师课程的复习总结

你可能感兴趣的:(Python数据结构,数据结构)