1 函数参数

函数的实参和形参个数可以不等,之所以会这样,原因是 ECMAScript 中的参数在内部是用一个数组来表示的。函数接收到的始终都是这个数组,而不关心数组中包含哪些参数(如果有参数的话)。如果实参个数大于形参个数,多余的实参不传递值,但是在arguments中可以访问;如果形参个数大于实参,没有传递值的实参将自动被赋予 undefined 值。

2 arguments和this

所有的函数调用都会传递两个隐式参数:arguments和this。

实际上,在函数体内可以通过 arguments对象 来访问这个参数数组,从而获取传递给函数的每一个参数。arguments 对象只是与数组类似(它并不是 Array 的实例),因为可以使用方括号语法访问它的每一个元素(arguments[0]、argumetns[1]…),也使用 length 属性来确定传递进来多少个参数。

arguments对象的值永远与对应命名参数的值保持同步:

function doAdd(num1, num2) { arguments[1] = 10; alert(arguments[0] + num2); } 因为 arguments对象中的值会自动反映到对应的命名参数,所以修改 arguments[1],也就修改了 num2,结果它们的值都会变成 10。不过,这并不是说读取这两个值会访问相同的内存空间;它们的内存空间是独立的,但它们的值会同步。另外还要记住,如果只传入了一个参数,那么为 arguments[1]设置的值不会反应到命名参数中(num2保持undefined)。这是因为 arguments 对象的长度是由传入的参数个数决定的,不是由定义函数时的命名参数的个数决定的。

this参数引用函数的上下文,函数上下文来自于Java等面向对象语言,Java中的this依赖于函数声明。但是和Java不同,javascript中的this依赖于函数的调用方式,因此把this称为调用上下文很合适。一般函数有四种调用方式:简单函数调用;对象方法调用;作为构造函数调用;通过apply()和call()调用。这四种方式的主要区别就在于调用上下文不同:简单函数调用的上下文是window对象,方法调用的上下文是对象,构造函数的上下文是是新创建的对象实例。这些调用中函数的this指向都是固定的,但是只有apply()和call()调用可以自主定义上下文。

3 apply()/call():在特定的作用域中调用函数。

区别在于接收参数的方式不同:apply(argu1,argu2),argu1是函数运行的作用域(this),argu2是参数数组,可以传入arguments 对象或者参数数组;call(argu1,argu2), argu1是this,argu2是逐个列出的函数参数。

如果你打算直接传入 arguments 对象,或者包含函数中先接收到的也是一个数组,那么使用 apply()肯定更方便;否则,选择 call()可能更合适。(在不给函数传递参数的情况下,使用哪个方法都无所谓。)

传递参数并非 apply()和 call()真正的用武之地;它们真正强大的地方是能够扩充函数赖以运行的作用域。使用 call()(或 apply())来扩充作用域的最大好处,就是对象不需要与方法有任何耦合关系。


JavaScript函数式编程(0):函数基础 arguments、this、apply()、call()

当需要为函数指定上下文时,就有必要使用apply()和 call()了,一个具体的例子就是 回调函数 。假如对数组中的每个元素进行一次操作, 命令式编程 方式一般使用for循环遍历数组元素,但是 函数式编程 是编写一个函数,然后对每个数组元素运行该函数,区别在于函数式编程更有利于代码复用。对每个数组元素运行该函数有两种思路,一种是把数组元素作为参数传入,一种是把数组参数作为函数运行的上下文,这时就可以用到apply()和 call()。

function forEach(list, callback){ for(var n=0; n<list.length; n++){ callback.call(list[n], n); } } var colors = ["blue", "red","green"]; var res = []; forEach(colors, function(index){ res[index] = (this == colors[index]); return res;//true,true,true }); alert(res);

使用callback回调函数的call方法,将当前数组元素作为第一个参数传入,将当前数组索引作为第二个参数传入,这使得当前元素变为函数上下文,索引值作为callback()的参数。在callback()内部验证当前元素是否是上下文。

4 没有重载(overloading)

ECMAScirpt函数没有签名,因为其参数是由包含零或多个值的数组来表示的。而没有函数签名,真正的重载是不可能做到的。如果在 ECMAScript 中定义了两个名字相同的函数,则该名字只属于后定义的函数。

函数重载定义:重载函数是函数的一种特殊情况,为方便使用,C++允许在同一范围中声明几个功能类似的同名函数,但是这些同名函数的形式参数(指参数的个数、类型或者顺序)必须不同,也就是说用同一个运算符完成不同的运算功能。这就是重载函数。重载函数常用来实现功能类似而所处理的数据类型不同的问题。

本文前端(javascript)相关术语:javascript是什么意思 javascript下载 javascript权威指南 javascript基础教程 javascript 正则表达式 javascript设计模式 javascript高级程序设计 精通javascript javascript教程

分页:12
转载请注明
本文标题:JavaScript函数式编程(0):函数基础 arguments、this、apply()、call()
本站链接:http://www.codesec.net/view/480802.html
分享请点击:


1.凡CodeSecTeam转载的文章,均出自其它媒体或其他官网介绍,目的在于传递更多的信息,并不代表本站赞同其观点和其真实性负责;
2.转载的文章仅代表原创作者观点,与本站无关。其原创性以及文中陈述文字和内容未经本站证实,本站对该文以及其中全部或者部分内容、文字的真实性、完整性、及时性,不作出任何保证或承若;
3.如本站转载稿涉及版权等问题,请作者及时联系本站,我们会及时处理。
登录后可拥有收藏文章、关注作者等权限...
技术大类 技术大类 | 前端(javascript) | 评论(0) | 阅读(54)