上一篇最后给出了用递归完成字符串逆置的代码,但是没有分析它的具体算法,今天做了如'abcde'字符串递归翻转的图跟大家分享(画的比较烂,具体思路还是有的,详情见附件)
这里的递归调用没有出现在函数末尾,二前面几个递归都出现在函数末尾,所以说递归可以分为在函数末尾的递归与在函数中的递归。其差别如下。
1.在函数尾部的递归,都可以用循环的方式做下去,这样的递归大多数情况只能造成代码的简洁,并不利于机器的运算。
2.在函数中间的递归,不一定能用循环的方式做下去,这样的递归有的可以转化成在函数末尾的递归,有的并不能。如上一篇所写的两种形式的代码,把再函数中间的递归转化成了在函数末尾的递归。
3.递归调用多用于二叉树的运算中,在函数中用递归可能会造成程序的低效,如斐波那契数列的求解(a1=1,a2=1,an=an-1+an-2......)实现代码如下:
int fib(int n) { int result; int pre_result; int next_older_result; result = pre_result = 1; while (n > 2) { n -= 1; next_older_result = pre_result; pre_result = result; result = pre_result + next_older_result; } return result; }
如果令n=50,机器会跑得很慢。
然而有些算法就是用递归的方式定义的,如求一个数的阶乘实现代码如下
int factorial(int n) { int result = 1; while (n > 1) { result *= n ; n -= 1; } return result; }
这样极大的简便了运算。
简而言之,递归的调用需要谨慎,有时候循环比递归更简便,运用递归是需思量,是否有更简便的循环。
如有不足希望批评指正