arguments对象表示 参数集合,它是一个伪类数组,拥有与数组相似的结构,可以通过数组下标的形式访问函数实参值,但是没有基础Array的原型方法。
1、没有定义形参,但在函数体内 可以通过arguments对象获取传递给该函数的每一个实参值。
function f(){ //没有定义形参的函数 for(var i = 0;i < arguments.length;i++){ //循环读取 函数的arguments对象 alert(arguments[i]); //显示指定下标的实参的值 } } f(3,7,9); //逐个显示每个传递的实参
arguments对象仅能够在函数体内使用,作为函数的属性而存在。用户可以通过点运算符访问arguments对象 。由于arguments对象在 函数体是可见的,也可以直接引用arguments对象。
2、arguments对象可以随时编辑实参值。可以使用for循环遍历 arguments 对象,然后把循环变量的值传递给实参,以便动态改变实参值。
function f(){ //没有定义形参的函数
for(var i = 0;i < arguments.length;i++){ //循环读取 函数的arguments对象 arguments[i] = i;//修改每一个是实参的值 alert(arguments[i]); //显示指定下标的实参的值 } } f(3,7,9); //返回提示1、2、3
3、通过修改arguments对象的length属性值,也可以达到改变函数实参个数的目的。当length属性值增大时,增加的实参值为undefined,如果length属性值减小,会丢弃arguments 数据集合后面对应个数的元素。
function f(){ //没有定义形参的函数 var length = arguments.length = 2; for(var i = 0;i < length;i++){ //循环读取 函数的arguments对象 alert(arguments[i]); //显示指定下标的实参的值 } } f(3,7,9); //返回提示3,7
4、arguments对象的回调函数:callee
arguments对象包含了一个callee属性,它引用当前arguments对象所属的函数,使用该属性可以在函数体内调用函数自身。在匿名函数中,callee属性比较有用,利用他可以设计函数迭代操作。
function f(x,y,z){ //没有定义形参的函数
var a = arguments.length;//获取函数实参的个数 var b = argumrnts.callee.length;//获取函数形式参数的个数 if(a != b){ //如果形参和实参个数不相等,则提示错误信息 throw new error("传递的参数不匹配"); }else{ //如果形参和实参数目相同,则返回它们的和 return x+y+z; } } alert(f(3,7,9)); //返回值为19 alert(f(1,5,7,5)); //提示错误
如果不是匿名函数,arguments.callee等价于函数名。
function f(x,y,z){ //没有定义形参的函数 var a = arguments.length;//获取函数实参的个数 var b = f.length;//获取函数形式参数的个数 if(a != b){ //如果形参和实参个数不相等,则提示错误信息 throw new Error("传递的参数不匹配"); }else{ //如果形参和实参数目相同,则返回它们的和 return x+y+z; } } alert(f(3,7,9)); //返回值为19
arguments对象的应用
灵活使用arguments对象,可以提升使用函数的灵活性,增强函数在抽象编程中的适应能力和纠错功能 。
1、如果函数参数个数不确定,或者函数的参数个数很多,而又不想为每个参数都定义一个形参变量,此时可以省略参数,直接在函数体内使用arguments对象来访问调用函数的实参值。
比如求平均值。
function avg(){ var num = 0, l = 0;//声明并初始化临时变量 for(var i = 0;i < arguments.length;i++){ if(typeof arguments[i] != "number") continue; num += arguments[i]; l++; } num /= l; return num; } alert(avg(3,5,7,9));//返回6
2、验证函数参数的合法性,比如用于判断邮箱
function isEmail(){ if(arguments.length > 1) throw new Error("只能够传递一个参数"); //检测参数个数 //定义正则表达式 var regexp = /^\w+((-\w)|(\.\w+))*\@[A-Za-z0-9]+((\.|-)[A-Za-z0-9]+)*\.[A-Za-z0-9]+$/; if(arguments[0].search(regexp) != -1) return true; //如果匹配则返回true。 else return false; } var email ="[email protected]"; alert(isEmail(email)); //返回为true
3、模拟java中的重载。
function sayHello(){ switch(arguments.length){ case 0: return "Hello world!"; case 1: return "Hello,"+arguments[0]; case 2: return (arguments[1] == "cn" ? "你好," :"Hello,")+arguments[0]; default: throw new Error("参数错误"); }; } alert(sayHello()); alert(sayHello("king")); alert(sayHello("king","cn"));
4、callee是arguments对象的一个属性,其值是当前正在执行的function对象。它的作用是使用匿名function可以被递归调用。计算斐波那契序列中第N个数的值的过程来演示arguments.callee的使用。
function fibonacci(num){ return (function(num){ if(typeof num != "number") return -1; num = parseInt(num); if(num < 1) return -1; if(num == 1 || num == 2) return 1; return arguments.callee(num - 1) + arguments.callee(num - 2); })(num); } alert(fibonacci(100));