10级台阶问题

本文探讨了经典的爬楼梯问题,通过动态规划的方法解决了该问题,并对比了几种不同的算法实现方式,包括递归算法、备忘录算法及动态规划算法。

问题一:爬楼梯

有一座高度是10级台阶的楼梯,从下往上走,每跨一步只能向上1级或者2级台阶。要求用程序来求出一共有多少种走法。

动态规划的思想:dynamic programming,一种分阶段求解决策问题的数学思想。即大事化小,小事化了。

分两部分:问题建模和求解问题。

(1)问题建模

上述问题假设只差一步走到第10级,则F(10)=F(9)+F(8)。(最优子结构)

.......

我们归纳出的公式如下:

F(1)=1;

F(2)=1;(边界)

.........

F(n)=F(n-1)+F(n-2);(状态转移公式)

动态规划中包含三个重要的概念:最优子结构、边界和状态转移公式

(2)求解问题

方法1:递归算法

package com.dynamicProgramming_lc;

public class DpDemo {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		System.out.println(getClimbingWays(10));
	}

	private static int getClimbingWays(int n){
		if (n<0) {
			return 0;
		}
		if (n==1) {
			return 1;
		}
		if (n==2) {
			return 2;
		}
		return  getClimbingWays(n-1)+getClimbingWays(n-2);
	}
}


分析可知:算法时间复杂度过高,达到了O(2^n),观察递归可知,出现了很多重复的f(*),可将f(*)放入map中,用时取出即可。

方法2:备忘录算法

package com.dynamicProgramming_lc;

import java.util.HashMap;
import java.util.Map;

public class DpDemo {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		Map<Integer, Integer> map = new HashMap<Integer, Integer>();
		System.out.println(getClimbingWays(map, 10));
	}

	private static int getClimbingWays(Map<Integer, Integer> map, int n){
		if (n<0) {
			return 0;
		}
		if (n==1) {
			return 1;
		}
		if (n==2) {
			return 2;
		}
		if (map.containsKey(n)) {
			return map.get(n);
		} else {
			int value = getClimbingWays(map, n-1)+getClimbingWays(map, n-2);
			map.put(n, value);
			return value;
		}
	}
}
方法3:动态规划算法

上述均为自顶向下计算,换种思路,自底向上计算,不使用递归。只需记住上次和上上次的走法数即可。


package com.dynamicProgramming_lc;

public class DpDemo {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		System.out.println(getClimbingWays(10));
	}

	private static int getClimbingWays(int n){
		if (n<0) {
			return 0;
		}
		if (n==1) {
			return 1;
		}
		if (n==2) {
			return 2;
		}
		int a = 1;
		int b = 2;
		int temp = 0;
		for (int i=3;i<n;i++) {
			temp = a + b;
			a = b;
			b = temp;
		}
		return temp;
	}
}
其时间复杂度为O(n),空间复杂度为O(1)。
上述问题只有一个变化维度,较简单。

问题二:国王和金矿

123

123

参考:http://mp.weixin.qq.com/s/0AgJmQNYAKzVOyigXiKQhA

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值