拾遗:关于“尾递归”- tail recursion
定义[个人理解]:
尾递归,即是将外层得出的常量计算因子,以函数参数的形式逐层向内传递,即内层调用整合外层调用的产出,整个递归的结果最终由最内层的一次函数调用得出;而通常的递归则是外层调用阻塞、等待内层调用的产出,最后由最上层的一次函数调用得出最终结果。
优执:
适度应用,可以带来效率的提升,同时在一定程度上提升程序的稳定性。
局限:
效率提升取决于编译器的优化策略,最终结果存在不确定性,即使内层调用在逻辑上已可独立运行;
仅可作为潜在的效率提升措施,但不能做为循环的替代,因为其不能保证 100% 避免栈溢出风险;
现代编译器已足够智能,结构简单的普通递归可被自动优化为尾递归,过度沉迷尾递归的结构得不偿失。
示例:
如在 clang-4.0 环境下, 在本已测试良好的尾递归函数中添加如下两句,将导致尾递归失效,从而爆栈使程序崩溃!
int A[ * * ];
printf("%p", &A);
结论:
偶尔惊艳,但不实用,不可作为常规手段。
拾遗:关于“尾递归”- tail recursion的更多相关文章
- 尾递归(Tail Recursion)和Continuation
递归: 就是函数调用自己. func() { foo(); func(); bar(); } 尾调用:就是在函数的最后,调用函数(包括自己). foo(){ return bar(); } 尾递归:就 ...
- Scala Tail Recursion (尾递归)
Scala对尾递归进行了优化,甚至提供了专门的标注告诉编译器需要进行尾递归优化.不过这种优化仅限于严格的尾递归,间接递归等情况,不会被优化. 尾递归的概念 递归,大家都不陌生,一个函数直接或间接的调用 ...
- 用尾递归和普通递归实现n!算法,二者比较
尾递归 - Tail Recursion尾递归是针对传统的递归算法而言的, 传统的递归算法在很多时候被视为洪水猛兽. 它的名声狼籍, 好像永远和低效联系在一起.尾递归就是从最后开始计算, 每递归一次就 ...
- Scala尾递归
递归函数应用 首先,我们来对比两个递归方法的求值步骤. 假设有方法gcd,用来计算两个数的最大公约数.下面是欧几里得算法的实现: def gcp(a: Int, b: Int): Int = if ( ...
- 泛函编程(3)-认识Scala和泛函编程
接着昨天的文章,再示范一个稍微复杂一点的尾递归tail recursion例子:计算第n个Fibonacci数.Fibonacci数第一.第二个数值分别是0,1,按顺序后面的数值是前面两个数的加合.例 ...
- haskell中的cps
cps全称叫continuation passing style,简要来讲就是告诉函数下一步做什么的递归方式,由于普通递归有栈溢出的问题,而cps都是尾递归(tail recursion),尾递归则是 ...
- Scala 常用语法
Clojure首先是FP, 但是由于基于JVM, 所以不得已需要做出一些妥协, 包含一些OO的编程方式 Scala首先是OO, Java语法过于冗余, 一种比较平庸的语言, Scala首先做的是简化, ...
- 递归、尾递归和使用Stream延迟计算优化尾递归
我们在学数据结构的时候必然会接触栈(Stack),而栈有一个重要的应用是在程序设计语言中实现递归.递归用途十分广泛,比如我们常见的阶乘,如下代码: 1234 public static int (in ...
- scala tail recursive优化,复用函数栈
在scala中如果一个函数在最后一步调用自己(必须完全调用自己,不能加其他额外运算子),那么在scala中会复用函数栈,这样递归调用就转化成了线性的调用,效率大大的提高.If a function c ...
随机推荐
- 92、R语言分析案例
1.读取数据 > bank=read.table("bank-full.csv",header=TRUE,sep=";") > 2.查看数据结构 & ...
- CentOS系统更换软件安装源yum
第一步:备份你的原镜像文件,以免出错后可以恢复. mv /etc/yum.repos.d/CentOS-Base.repo /etc/yum.repos.d/CentOS-Base.repo.back ...
- Django 自定义模型管理器(Manager)及方法
转载自:https://www.cnblogs.com/sui776265233/p/11571418.html 1.自定义管理器(Manager) 在语句Book.objects.all()中,ob ...
- 论一个PHP项目上线的注意点
一.后端问题 服务器配置要跟上流量 预估QPS时要给足未知流量的空间 后端数据库设计要根据项目大小来相对应,小型流量单表就可以,但是中大型要分库分表 在处理执行修改的操作时一定要多一层判断(判断是否已 ...
- Msys2编译Emacs
Msys2编译Emacs */--> code {color: #FF0000} pre.src {background-color: #002b36; color: #839496;} Msy ...
- CTU OPEN 2017 Pond Cascade /// 思维
题目大意: 给定N F 给定N个水池的大小 每个水池都以流量F开始注水 当位置较前的水池注满后 水会溢出到下一个水池 求 最后一个水池开始溢出的时间 和 所有水池全部注满的时间 1.最后一个n水池开始 ...
- ReentrantReadWriteLock的相关使用
ReentrantLock具有完全互斥排他的效果,同一时间只有一个线程执行ReentrantLock.lock()方法后面的任务,这样虽然能够保证线程安全性,但是效率是比较低的 ReentrantRe ...
- shell位置参数和 shift 命令
- Jmeter请求非Json格式的参数如何添加
Step1: 可以先在用户自定义变量中加入你需要添加的请求类型,具体参考图片 Step2: 在线程组下请求之前添加HTTP信息头管理器
- 添加ali yum源
wget -O /etc/yum.repos.d/CentOS-Base.repo http://mirrors.aliyun.com/repo/Centos-7.repo #yum clean a ...