数据结构 C 从累加的递归实现到汉诺塔问题

 累加的递归实现

 同样是累加,递归实现的时间复杂度为O(),空间复杂度为O();而使用for循环的时间复杂度为O(),空间复杂度为O(),

#include<stdio.h>
/*递归累加
*系统将未运行完的reursiveAdd(paraN)压入栈中,等待recursiveAdd(paraN-1)算完 
*/
int recursiveAdd(int paraN){
	printf("Entering recursiveAdd(%d)\r\n",paraN);
	if(paraN<=0){
		printf("return 0\r\n");
		return 0;
	}
	else{
		printf("return recursiveAdd(%d)+%d\r\n",paraN-1,paraN);
		return recursiveAdd(paraN-1)+paraN;
	}
}
void recursiveAddTest(){
	int n,num;
	printf("---- RecursiveAddTest begins ----\r\n");
	n=-1;
	num=recursiveAdd(n);
	printf("The result of recursiveAdd(%d) is %d\r\n",n,num);
	n=1;
	num=recursiveAdd(n);
	printf("The result of recursiveAdd(%d) is %d\r\n",n,num);
	n=5;
	num=recursiveAdd(n);
	printf("The result of recursiveAdd(%d) is %d\r\n",n,num);
	printf("---- RecursiveAddTest ends ----\r\n");
}
int main(){
	recursiveAddTest();
	return 0;
}

运行结果

 图解累加递归实现:以recursiveAdd(5)为例

 1.要算recursiveAdd(5),需要算recursiveAdd(4),但recursiveAdd(5)还没算完,于是系统将其压入栈中(recursiveAdd(4)等同理)

 2.算recursiveAdd(1)时需要算recursiveAdd(0),而recursiveAdd(0)返回了0,那么recursiveAdd(1)得以继续计算,返回recursiveAdd(0)+1,这时recursiveAdd(1)计算完毕,出栈;同理,recursiveAdd(2)等也得以继续计算,并相继出栈。

 

 汉诺塔问题

#include<stdio.h>
void Hanoi(int paraN,char paraSource,char paraDestination,char paraTransit){
	if(paraN<=0){
		return;
	}
	else{
		Hanoi(paraN-1,paraSource,paraTransit,paraDestination);
		printf("%c -> %c\r\n");
		Hanoi(paraN-1,paraTransit,paraDestination,paraSource);
	}
}
void HanoiTest(){
	int n;
	printf("---- HanoiTest begins. ----\r\n");
	printf("---------------n=1-------------\r\n");
	n=1;
	Hanoi(n,'A','B','C');
	printf("---------------n=2-------------\r\n");
	n=2;
	Hanoi(n,'A','B','C');
	printf("---------------n=3-------------\r\n");
	n=3;
	Hanoi(n,'A','B','C');
	printf("---------------n=4-------------\r\n");
	n=4;
	Hanoi(n,'A','B','C');
	printf("---- HanoiTest ends. ----\r\n");
}
int main(){
	HanoiTest();
	return 0;
}

运行结果 

 ---- HanoiTest begins. ----
---------------n=1-------------
B -> C
---------------n=2-------------
C -> B
A -> C
B -> A
---------------n=3-------------
B -> C
A -> B
C -> A
B -> C
A -> B
C -> A
B -> C
---------------n=4-------------
C -> B
A -> C
B -> A
C -> B
A -> C
B -> A
C -> B
A -> C
B -> A
C -> B
A -> C
B -> A
C -> B
A -> C
B -> A
---- HanoiTest ends. ----

--------------------------------
Process exited after 0.04675 seconds with return value 0
请按任意键继续. . .

 手动函数调用过程图:

以n=3为例,

Hanoi(3,s,d,t)需要执行三步:1.执行Hanoi(2,s,t,d) 2.printf(s->d) 3.执行Hanoi(2,t,d,s);

但执行1.Hanoi(2,s,t,d)时也需要执行三步:1.执行Hanoi(1,s,d,t) 2.printf(s->t) 3.执行Hanoi(2,d,t,s);

所以Hanoi(3,s,d,t)被系统压入栈中,等待1.Hanoi(2,s,t,d)2.printf(s->d) 3.执行Hanoi(2,t,d,s);完毕执行

Hanoi(2)同理,需要等Hanoi(1),所以Hanoi(2)也会被压入栈中.....

Hanoi的时间复杂度和空间复杂度:

时间复杂度:O(n)=2^n

空间复杂度:O(n)=n

因为栈的原因,有空间复用,因此hanoi的空间复杂度远小于时间复杂度

心得体会: 

 手动跟着老师的代码将函数调用过程写一遍,会对Hanoi递归调用的理解好得多

 使用递归有些时候的确时间复杂度会好很多,但是它理解很困难,并且不好对变量进行追踪,这也许就是为什么老师说出现了递归多半都是高级程序的原因吧

 

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值