递归 & 汉诺塔

定义:

一个方法可以调用另一个方法来帮助它完成目标。同样,一个方法也可以调用它自身以完成目标。

递归:一种允许方法调用该方法自身的编程技术。

能否递归的编程的关键在于能否递归的思考。

递归体包含两部分:递归部分和非递归部分,非递归部分作为称为基本情形,是递归的统一出口,起到终止递归的作用。如果一个递归没有定义非递归部分,这种递归就是无穷递归,类似于无穷循环,只不过这时是递归定义的内部出现了“循环”。

 

有一些问题可以用递归解决,也就可以用迭代解决。

递归是有些问题最优雅最恰当的解决方式,但是解决有些问题递归并没有迭代那么直观。不过有些情况下,迭代会过于复杂,递归可以创造相对短小且优雅的程序。

例子:

1到n的累加器:

递归实现:

public int sum(int n){

      int res = 0;

    if(n == 1){
        res = 1;
      }else{
        res = n + sum(n - 1);
      }

      return res;
   }

迭代实现:

public int sum(int n){

      int res = 0;

      for(int i = 0; i <= n; i++){
        res += i;
      }

      return res;
   }

递归可以分为直接递归和间接递归。

        方法调用方法自身叫直接递归。方法调用另一个方法,另一个方法继续调用其它方法,最后调用的那个方法再调用第一个方法,依次类推,这样的递归叫间接递归。如f1调用f2f2调用f3f3调用f4f4再调用f1就属于间接递归。

间接递归的例子:

   public int f1(int x) {

      if (x <= 0) return x;
         return f2(x);
   }

   public int f2(int y) {
      return f1(y - 1);
   }

递归优雅的极致展现:

汉诺塔例子:

        在汉诺塔问题中有3根竖直的柱子和一组圆盘,圆盘中间有一个孔,这样它们就能够在柱子上滑动,每一张圆盘的直径都不同。开始时候,所有圆盘按照直径大放下面依次放在一个柱子上。

汉诺塔问题的目标就是把所有圆盘从初始柱子(start)移动到最终的柱子(end)上,可以已用临时柱子(temp)作为辅助。

移动必须遵循的原则:

1.一次只能移动一个盘子;

2.不能将大的圆盘放到小的圆盘上面;

3.所有圆盘都必须放在柱子上。

 

将一叠圆盘(N个)从start移动到end的解决方法:

1.将最上方的N-1个圆盘从start移动到temp

2.将第N个圆盘从start移动到end

3.N-1个圆盘从temp移动到end

HanoTower.java

/*
*Created on 2016年5月26日
*Copyright 2016 Yong Cai Limited crop. All Rights Reserved
*
*728**80@qq.com
*/

package org.cy.com;

public class HanoTower {
	private int totalDisks;
	
	public HanoTower(int disks){
		this.totalDisks = disks;
	}
	
	public void solve(){
		moveTower(totalDisks, 1, 2, 3);
	}
	
	private void moveTower(int diskNums, int start,int temp, int end){
		if(diskNums == 1){
			moveOneDisk(start, end);
		}else{
			moveTower(diskNums - 1, start, end, temp);
			moveOneDisk(start, end);
			moveTower(diskNums - 1, temp, start, end);
		}
	}
	
	private void moveOneDisk(int start, int end){
		System.out.println("move from " + start + " to " + end);
	}
	
}
Main.java

/*
*Created on 2016年5月26日
*Copyright 2016 Yong Cai Limited crop. All Rights Reserved
*
*728**80@qq.com
*/

package org.cy.com;

public class Main {

	public static void main(String[] args) {
		HanoTower ht = new HanoTower(2);
		ht.solve();
	}

}


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值