递归我们不陌生,

  那什么是尾递归呢?

  为什么要用尾递归呢?

  尾递归怎么用呢?

  带着这三个问题我们来了解它,

我们知道递归非常耗费内存,一不小心就会发生‘栈溢出’, 相信你一定遇到过这个错误: stack overflow,

尾递归就是用来优化递归的这个问题的。

  尾递归的定义: 在函数的最后一步返回自身,也就是显示地return自身就称为尾递归。对于尾递归来说,

由于只存在一个调用帧,所以永远不会发生‘栈溢出’。

  我们来举例说明尾递归的好处:

  • 比如计算n的阶乘, 我们首先想到找规律, n的阶乘等于n* (n-1)的阶乘
  • 找出口1的阶乘等于1
  • 然后我们就很自然的用递归写出
  • function jieCheng(n) {
    if (n===1) {
    return 1
    }
    return n * jieCheng(n -1);
    }
    const result = jieCheng(5); console.log(result); //

    很自然, so easy有木有,

   but,  这样我们每递归一次,上一次的调用记录还保存着, 也就是说我们计算n的阶乘最多要保存n个调用记录,复杂度为O(n).

   改成尾递归:

   

function weiJieCheng(n, total=1) {
if (n === 1) {
return total;
}
return weiJieCheng(n-1, n * total);
} console.log(weiJieCheng(5), 'wei'); //

  把中间变量改写成函数的参数, 这样就只保存了一个调用记录,复杂度为O(1)。

  再用蹦床函数对尾递归进行优化,把递归执行转换成循环执行:

function trampoline(f) {
while(f && f instanceof Function) {
f = f ();
}
}
trampoline(weiJieCheng(5, 1))

最新文章

  1. appium 自动化测试之知乎Android客户端
  2. 烂泥:NFS做存储与KVM集成
  3. ERROR 1045 (28000): Access denied for user 'root'@'localhost'
  4. WAMP(Windows+Apache+Mysql+PHP)环境搭建
  5. codeforces55D数位dp
  6. MVC源码解析 - 目录
  7. Bitmap与Matrix旋转ImageView
  8. Django使用遇到的各种问题及解决方法
  9. 原生Js写轮播图代码
  10. log4j警告:WARN Please initialize the log4j system properly 的解决方法
  11. Mysql 常用SQL语句集锦
  12. 1.python函数式编程-map函数
  13. MySQL分布式实现ID自增
  14. Android Dagger 2 无法自动生成 Dagger Component
  15. getImplementationVersion-获取版本号
  16. modelsim仿真中遇到的问题
  17. jre安装配置!
  18. OpenSSL 中 RSA 加密解密实现源代码分析
  19. java实际项目中interface和abstract interface 区别
  20. Android签名生成和互转

热门文章

  1. 【比赛游记】CSP2019游记
  2. 201871010106-丁宣元 《面向对象程序设计(java)》第十一周学习总结
  3. 201871010108-高文利《面向对象程序设计(java)》第六七周学习总结
  4. 【我的第一个现实漏洞分析】 CVE-2017-17215 华为智能路由器HG532 漏洞分析笔记
  5. (day45)JavaScript
  6. shell的变量以及常见符号
  7. Linux学习笔记-第8天 - 看似很简单
  8. tornado内置接口调用顺序initialize\prepare...
  9. 为什么accpet会重新返回一个套接字
  10. Function.prototype.call.bind