递归解决汉诺塔问题和青蛙跳台阶问题

编程只是工具,是用来处理问题的。学习中老师提出两个问题让试着用递归解决。

第一题

汉诺塔问题

有三根柱子A、B、C,其中A柱上按大小有序排列N个圆盘,底部最大,顶部最小。要求把圆盘从下面开始按大小顺序重新摆放在C柱上。并且规定,在小圆盘上不能放大圆盘,在三根柱子之间一次只能移动一个圆盘。求从A柱往C柱上挪动N个圆盘最少需要多少步。

这个问题很明显可以如此分析,将圆盘分为最低部一个,和上面N-1个两部分,只需将上面N-1个圆盘放在B柱上,再将底部圆盘放在C柱上,然后将B柱上N-1个圆盘放到C柱上即可。相应的,上面N-1个,可以分解为第N-1个和其上方N-2个的两部分。

由以上分析可知,第N个圆盘的最少步数为(第N-1个圆盘的最少步数)+1+(第N-1个圆盘的最少步数)。明显可以通过大事化小的思路解决,与递归的思路相符,以下测试:

#include <stdio.h>

//汉诺塔问题最优步数求解。
int tow(int x)
{
	if (x > 1)
		return 2 * tow(x - 1) + 1;	//重复前一步骤并将底盘放入目标杆。
	else
		return 1;
}

int main()
{
	int n = 0;
	scanf("%d", &n);
	printf("%d\n", tow(n));
	return 0;
}

输入n=3层时,函数tow(3)执行 return  2*tow(3 -1) +1,进入下一层tow(2),执行return 2*tow(2-1) +1,进入下一层tow(1),执行return 1。回到上一层结果 return 2*1+1(=3),再回到上一层结果 return 2*3 +1(=7)。

经多次测试,计算结果正确。

第二题

青蛙跳台阶问题

有个青蛙,一次可以跳1层台阶,也可以跳2层台阶。问它跳到N层台阶有多少种可能的跳法。

这个问题也比较简单。第一层只有一种可能,跳1层。第二层只有两种可能,跳1层或跳2层。第N(N>2)层也只有两种可能,分别是从(N - 1)层再跳1层,从(N-2)层再跳2层。即第N层可能的跳法数量为(N-1)的可能跳法数量加上(N-2)的可能跳法数量。也符合递归的思路,把大事化小。以下测试:


#include <stdio.h>

//青蛙跳台阶,每次跳1层或2层,到n层可能的跳法数量。
int step(int x)
{
	if (x > 2)
		return step(x - 1) + step(x - 2);	//由之前一层+1层,或由之前两层+2层。
	else if (x == 2)
		return 2;
	else
		return 1;
}

int main()
{
	int n = 0;
	scanf("%d", &n);
	printf("%d\n", step(n));
	return 0;
}

分析思路同上例。

输入n=4层时,函数step(4)执行return step(3) +step(2); 函数step(3)执行return step(2)+step(1);函数step(2)执行返回2;函数step(1)执行返回1;则回到上一级,step(3)=2+1=3;再回到上一级,step(4)=3+2=5。

此类问题解决思路都是先将后续可能分解成更小级别的问题,即把大事化小。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值