递归函数大家都应该比较熟吧?那么,如何在javascript中书写一个完美的递归函数呢?且听我娓娓道来。

递归函数

写的时候,查了一下维基百科对递归函数的定义,恕我愚钝,简直太深奥了!所以,我还是简单的说说我对递归函数的理解吧。递归函数,说白了就是在函数内部引用函数自身,最终到给定的递归结束条件时回溯。当然,你也可以不给定结束条件,死了别挂我(╯﹏╰)

使用javascript书写递归函数

现在,一步一步,摩擦摩擦,在皎洁的编辑器上,来开始使用javascript写递归函数吧!

function fun(num){
if(num <= 1){
return 1;
} else{
return num * fun(--num);
}
}

好了,不错,一个堪称经典的递归求阶乘的函数诞生了。事情肯定不会这么顺利,一定是个圈套。我们来如下调用以下看看会怎么样?

var test = fun;
fun = null;
console.log(test(7));

呵呵,居然报错了

Uncaught TypeError: object is not a function

嗯,报了类型错误。。。

回过头去看看我们是如何调用的。发现问题了吧!我们把fun赋给了test,然后把fun给回收掉了。为什么会出错呢?因为像function这种赋值其实是引用传递,只是把指向函数的指针(这里说地址也行)赋给test了。但我们把fun赋值为null的时候,函数都已经被回收了,拿什么来执行?知道问题所在了,我决定换种方式来定义:

function fun(num){
if(num <= 1){
return 1;
} else{
return num * arguments.callee(--num);
}
}

然后测试一下:

var test = fun;
fun = null;
console.log(test(7));

OK,测试通过!

但是在某一天,当我实际码代码的时候,问题又出现了。什么问题呢?我们来看一下:

Uncaught TypeError: 'caller', 'callee', and 'arguments' properties may not be accessed on strict mode functions or the arguments objects for calls to them

╮(╯▽╰)╭哎!可怜啊!因为我使用了"use strict"!严格模式下是不允许的。。。

好吧!继续想办法!既然不能使用arguments.callee(),那还是想想其他的方式吧。

看下面的代码:

var fun = (function f(num){
if(num <= 1){
return 1;
} else{
return num * f(--num);
}
});

然后我测试了以下,神奇的通过了,暂时没有发现任何问题!

为什么呢?因为我们使用了“()”,巧妙地使用命名函数表达式来达到了同样的效果。

参考资料

  1. 《JavaScript高级程序设计(第三版)》
  2. 《JavaScript启示录》

如何使用javascript书写递归函数的更多相关文章

  1. JSPatch 可以让你用 JavaScript 书写原生 iOS APP

    简介   JSPatch 可以让你用 JavaScript 书写原生 iOS APP.只需在项目引入极小的引擎,就可以使用 JavaScript 调用任何 Objective-C 的原生接口,获得脚本 ...

  2. JavaScript 书写位置

    类似于 CSS 样式,JavaScript 也有三种不同位置的书写方式. 1.写在行内 <input type="button" value="按钮" o ...

  3. JavaScript中递归函数用法需要注意的

    <script> function sum(num){ if(num<=1){ return 1; }else{ return num*sum(num-1);//return num ...

  4. 规范javascript书写

    空白 缩进 换行限制 if while for do 2.  命名 常量 URL_CONFIG 变量 listLen 函数命名 调用函数  function setStyle(dom, name, v ...

  5. javaScript书写规范

    命名规范. 常量名    全部大写并单词间用下划线分隔    如:CSS_BTN_CLOSE.TXT_LOADING对象的属性或方法名    小驼峰式(little camel-case)    如: ...

  6. Javascript书写位置

    1.行内式js(很少使用) 以on开头,如onclick HTML中推荐双引号,JS推荐单引号 2.内嵌式js(常用) <script> alert('hello world'); < ...

  7. [译]Javascript中的递归函数

    本文翻译youtube上的up主kudvenkat的javascript tutorial播放单 源地址在此: https://www.youtube.com/watch?v=PMsVM7rjupU& ...

  8. JavaScript的书写格式及书写的注意点

    JavaScript书写格式: 1.行内样式: 写在标签内部 2.内嵌样式(内联样式) : 写在一对head标签中 3.外链样式: 写在一个单独的.js文件中, 再导入进来 JavaScript书写格 ...

  9. 常用html、CSS、javascript前端命名规范

    无论是从技术角度还是开发视角,对于web前端开发规范文档都有一定规范,本文就css3和html5的发展前景总结了一系列的web开发文档,仅供大家参考. 规范目的: 为提高团队协作效率, 便于后台人员添 ...

随机推荐

  1. codeforces 337D 树形DP Book of Evil

    原题直通车:codeforces 337D Book of Evil 题意:一棵n个结点的树上可能存在一个Evil,Evil危险范围为d,即当某个点与它的距离x<=d时,那么x是危险的. 现已知 ...

  2. C++ API设计

    <C++ API设计> 基本信息 作者: (美)Martin Reddy    译者: 刘晓娜 臧秀涛 林健 丛书名: 图灵程序设计丛书 出版社:人民邮电出版社 ISBN:97871153 ...

  3. Mysql知识要点总结

    1.安装 要点:记得更改字符集 2.数据类型 常用数据类型:INT VARCHAR BLOG 3.操作数据库 SHOW DATABASES; CREATE DATABASE 名称; DROP DATA ...

  4. 在Linux下怎么确定哪个网卡对应哪个接口?

    国内私募机构九鼎控股打造APP,来就送 20元现金领取地址:http://jdb.jiudingcapital.com/phone.html 内部邀请码:C8E245J (不写邀请码,没有现金送) 国 ...

  5. cocos2d-x CCTableView

    转自:http://www.cnblogs.com/dcxing/archive/2013/01/16/2862068.html CCTableView在游戏中一般用在背包这样场景或层中,当然也不止这 ...

  6. Codeforces Gym 100002 D"Decoding Task" 数学

    Problem D"Decoding Task" Time Limit: 1 Sec Memory Limit: 256 MB 题目连接 http://codeforces.com ...

  7. C#制作在线升级程序

    //这是一个webservice private AppUpdate.UpdateServ UpdateSvr; private void button1_Click(object sender, S ...

  8. win7中USB音箱没有声音解决的方法

    Win7装好后,原来在XP中工作正常的USB小音箱却不工作了,重装了声卡驱动还是一样,后来通过下面尝试最终好用了. 1.右键右下角喇叭button. 2.点击"播放设备". 3.设 ...

  9. PHP实现微博的同步发送(转)

    导读:在设计博客类站点时,有时会需要在发布文章时同步发布在微博上.本文阐述了实现该功能的基本方式. 准备工作   作为新浪微博的开发者,需要有身份验证: 个人身份认证的审核,一般一个工作日: 接着是提 ...

  10. MySQL Troubleshoting:Waiting on query cache mutex 腾讯数据库工程师:幕南风

    http://blog.itpub.net/26515977/viewspace-1208188/           今天被MySQL Query Cache 炕了.线上大量 Waiting on ...