【算法】递归法实现汉诺塔问题

来源:互联网 发布:阮星竹 知乎 编辑:程序博客网 时间:2024/06/07 12:52

递归法实现汉诺塔问题

这里的汉诺塔问题稍加改动:从“左”不能直接到“右”,必须先从“左”到“中”,再从“中”到“右”;从“右”到“左”同理;即只能在相邻的柱子间移动。

思路:

  • process(int num, String from, String to)函数,实现了第num块,从from柱子到to柱子的移动过程
  • 移动分为两类,相邻柱子的移动,不相邻柱子的移动(如果是传统的汉诺塔问题则不用如此分类)
  • 相邻柱子的移动:从"左"到"中"从"右"到"中"从"中"到"左"从"中"到"右"
      1. 上面的num - 1层,从from移到另一个柱子,即除了fromto的另一根柱子
      1. 然后第num块从fromto
      1. 上面的num - 1层从另一个柱子到to
  • 不相邻柱子的移动:从"左"到"右"从"右"到"左"
      1. 上面的num - 1层从fromto
      1. num块,从from移到middle
      1. 然后第num - 1块从tofrom
      1. num块,从middle移到to
      1. 上面的num - 1层从fromto
package com.lilydedbb;/** * Created by dbb on 2016/12/24. */public class HanoiProblemByRecursion {    private static String left = "left  ";    private static String mid = "middle";    private static String right = "right ";    public static int hanoiProblem(int num){        if (num < 1)            return 0;        return process(num, left, right);    }    // 返回的是步数    public static int process(int num, String from, String to){        // 只有一个的时候        if(num == 1){            if(from.equals(mid) || to.equals(mid)){                System.out.println("move 1 from " + from + " to " + to);                return 1;            }else{                System.out.println("move 1 from " + from + " to middle");                System.out.println("move 1 from middle to " + to);                return 2;            }        }        // 从"左"到"中",从"右"到"中",从"中"到"左",从"中"到"右"        if(from.equals(mid) || to.equals(mid)){            String another = (from.equals(left) || to.equals(left)) ? right : left;            int part1 = process(num - 1, from, another);            int part2 = 1;            System.out.println("move " + num + " from " + from + " to " + to);            int part3 = process(num - 1, another, to);            return part1 + part2 + part3;        } else { // 从"左"到"右",从"右"到"左"            int part1 = process(num - 1, from, to);            int part2 = 1;            System.out.println("move " + num + " from " + from + " to middle");            int part3 = process(num - 1, to, from);            int part4 = 1;            System.out.println("move " + num + " from middle to " + to);            int part5 = process(num - 1, from, to);            return part1 + part2 + part3 + part4 + part5;        }    }}

测试程序及测试结果如下:

int steps = HanoiProblemByRecursion.hanoiProblem(2);System.out.println("The Minimum step is " + steps);
move 1 from left   to middlemove 1 from middle to right move 2 from left   to middlemove 1 from right  to middlemove 1 from middle to left  move 2 from middle to right move 1 from left   to middlemove 1 from middle to right The Minimum step is 8Process finished with exit code 0
0 0
原创粉丝点击