Java递归解决汉诺塔问题(超详细,初学者也能看懂)

14 篇文章 1 订阅
9 篇文章 0 订阅

汉诺塔问题源自印度一个古老的传说,印度教的“创造之神”梵天创造世界时做了 3 根金刚石柱,其中的一根柱子上按照从小到大的顺序摞着 64 个黄金圆盘。梵天命令一个叫婆罗门的门徒将所有的圆盘移动到另一个柱子上,移动过程中必须遵守以下规则:

1.每次只能移动柱子最顶端的一个圆盘;

2.每个柱子上,小圆盘永远要位于大圆盘之上;

下面我将附上我的代码和解题思路:

代码如下:

/**
 * 汉诺塔问题
 */
public class HanNuota {
    public static void main(String[] args) {
        hanoi(3,'A','B','C');
        System.out.println("总的移动了:"+ (n-1) +"次");
    }

    //定义n来记录移动次数
    public static int n = 1;
    /**
     * 定义一个递归函数来实现汉诺塔的移动问题
     * @param num    汉诺塔层数
     * @param begin  开始柱
     * @param end    目标柱
     * @param middle 中转站
     */
    public static void hanoi(int num,char begin,char end,char middle){
        if(num == 1){
            //如果层数为1,直接将其移动到目标柱
            System.out.println("第"+ n +"次:从"+ begin +"移动到"+ end);
            n++;
        }else {
            //目前情况:begin上有num层,middle无,end无
            //把begin上面的num-1层移动到middle(这里把end和middle换位置,这样就把num-1层移到了middle上)
            hanoi(num-1,begin,middle,end);
            //目前情况:begin上有1层,middle上num-1有层,end无
            //把begin的那层移动到end
            System.out.println("第"+ n +"次:从"+ begin +"移动到"+ end);
            //目前情况:begin无,middle上有num-1层,end上有1层
            n++;
            //把middle的num-1层移动到end(这里把begin和middle换位置,这样就把num-1层移动到了end上)
            hanoi(num-1,middle,end,begin);
        }
    }
}

运行结果图如下:

结题思路及过程:

为了帮助大家更好的理解我的解题思路,在这里的解题过程精确到了每一步。

我在这里列举了层数为3时的运行过程,其它层数的仿照这个进行就能得到过程及结果。

//step1:    此时参数顺序为begin A,end B,middle C
    hanoi(3,begin A,end B,middle C){
        //step2(在step1的基础上):    把end和middle换位置,此时参数顺序为begin A,middle B,end C
        hanoi(2,begin A,middle B,end C){
            //在step2的基础上    把end和middle换位置,此时参数顺序为begin A,end B,middle C
            hanoi(1,begin A,end B,middle C){
                System.out.println("第"+ n +"次:从"+ begin +"移动到"+ end);//A->B
                n++;
            }
            System.out.println("第"+ n +"次:从"+ begin +"移动到"+ end);//A->C
            n++;
            //在step2的基础上    把begin和middle换位置,此时参数顺序为middle A,begin B,end C
            hanoi(1,middle A,begin B,end C){
                System.out.println("第"+ n +"次:从"+ begin +"移动到"+ end);//B->C
                n++;
            }
        }
        System.out.println("第"+ n +"次:从"+ begin +"移动到"+ end);//A->B
        n++;
        //step3(在step1的基础上):    把begin和middle换位置,此时参数顺序为middle A,end B,begin C
        hanoi(2,middle A,end B,begin C){
            //在step3的基础上    把end和middle换位置,此时参数顺序为end A,middle B,begin C
            hanoi(1,end A,middle B,begin C){
                System.out.println("第"+ n +"次:从"+ begin +"移动到"+ end);//C->A
                n++;
            }
            System.out.println("第"+ n +"次:从"+ begin +"移动到"+ end);//C->B
            n++;
            //在step3的基础上    把begin和middle换位置,此时参数顺序为begin A,end B,middle C
            hanoi(1,begin A,end B,middle C){
                System.out.println("第"+ n +"次:从"+ begin +"移动到"+ end);//A->B
                n++;
            }
        }
    }

以上的过程如果你有哪里看不懂的可以在评论区留言哦!

或者你有更好的理解方法,也可以在评论区分享给大家哦!

  • 8
    点赞
  • 23
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 5
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

欲戴王冠♛必承其重

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值