• jacascript 函数参数与 arguments 对象


    前言:这是笔者学习之后自己的理解与整理。如果有错误或者疑问的地方,请大家指正,我会持续更新!

      调用函数时,实参和形参需要一一对应,但如果参数多了的话,会很苦恼;

      我们可以用键值对(字面量对象)的方式传参,这样参数的顺序就无关紧要了

            <script type="text/javascript">
                function test4(name,age,height,pos){
                    return name+age+height+pos;
                }
                console.log(test4('Shane',25,172,'wuhan'));//Shane25172wuhan
                
                var person = {
                    name : 'Shane',
                    age : 25,
                    height : 172,
                    pos : 'wuhan'
                }
                function test5(obj){
                    return obj.name+obj.age+obj.height+obj.pos;
                }
                console.log(test5(person));//Shane25172wuhan
                console.log(test5({//匿名对象可也以
                    name : 'Shane',
                    age : 25,
                    height : 172,
                    pos : 'wuhan'
                }));//Shane25172wuhan
            </script>

      非严格模式下,相同的形参会被最后一个形参覆盖;

      严格模式不允许出现相同形参,会报错;

            <script type="text/javascript">
                function test(x,x,x){//非严格模式下,相同的形参会被最后一个形参覆盖;严格模式不允许出现相同形参,会报错
                    return x;
                }
                console.log(test(1,2,3));//3  
            </script>

      当实参比形参个数要少,剩下的形参都将设置为 undefined 值;

      当实参比形参个数要多,剩下的实参没有办法直接获得,需要使用即将提到的 arguments对象;

      在 Javascript 中,arguments 对象是当前函数的一个内置属性;

      arguments 非常类似 Array,但实际上又不是一个 Array 实例;

      arguments 对象的 length 属性显示实参的个数,函数的 length 属性显示形参的个数。

            <script type="text/javascript">
                function test2(x,y,z){
                    console.log(x,y,z);//1和2和undefined  
                }
                test2(1,2);
                
                function test3(x,y,z){
                    console.log(x,y,z);//1,2,3
                    console.log(arguments);//[1, 2, 3, 4]  arguments非常类似Array,但实际上又不是一个Array实例。
                    console.log(typeof arguments);//object
                    console.log(arguments instanceof Array)//false
                    console.log(arguments[0]);//1  
                    console.log(arguments[1]);//2  
                    console.log(arguments[2]);//3  
                    console.log(arguments[3]);//4  
                    console.log(arguments.length);//4  arguments对象的长度是由实参个数决定而不是形参个数决定的
                }
                test3(1,2,3,4);
                console.log(test3.length);//3  函数的length属性显示形参的个数
            </script>

      在非严格模式下,当形参与实参的个数相同时,arguments 对象的值和对应形参的值保持同步;

      虽然形参和对应 arguments 对象的值相同,但并不是相同的命名空间;

      但在严格模式下,arguments 对象的值和形参的值是独立的;

            <script type="text/javascript">
                function test6(x,y){
                    console.log(x,arguments[0]);//1 1  在非严格模式下,当形参与实参的个数相同时,arguments对象的值和对应形参的值保持同步;
                    console.log(y,arguments[1]);//2 2
                    
                    x = 345;
                    console.log(x,arguments[0]);//345 345 在非严格模式下,当形参与实参的个数相同时,arguments对象的值和对应形参的值保持同步;
                    arguments[1] = 789;
                    console.log(y,arguments[1]);//789 789
                }
                test6(1,2);
                
                function test7(x,y){
                    console.log(x,arguments[0]);//undefined undefined
                    
                    arguments[0] = 345;
                    console.log(x,arguments[0]);//undefined 345  
                    //当形参并没有对应的实参时,arguments对象的值与形参的值并不对应,所以形参和对应arguments对象是不同的命名空间;
                }
                test7();
                
                function test8(x,y){
                    'use strict'; //定义严格模式
                    console.log(x,arguments[0]);//3 3
                    
                    arguments[0] = 456;
                    console.log(x,arguments[0]);//3 456    在严格模式下,arguments对象的值和形参的值是独立的;
                    x = 789;
                    console.log(x,arguments[0]);//789 456
                }
                test8(3);
            </script>

       在未知参数数量的情况下,可以用 arguments

            <script type="text/javascript">
                //在未知参数数量的情况下,可以用arguments
                function add(){
                    var sum = 0;
                    for(var i = 0; i < arguments.length; i++){
                        sum += arguments[i];  //参数累加
                    }
                    return sum;
                }
                console.log(add(0));//0
                console.log(add(0,1,2,3));//6
            </script>

      arguments 对象有一个 callee 属性,该属性是一个指针,指向拥有这个 arguments 对象的函数,也就是函数本身;

      arguments.callee() 返回此 arguments 对象所在的当前函数引用。在使用函数递归调用时推荐使用 arguments.callee 代替函数名本身。

      function.caller() 返回一个对当前函数的引用,该引用调用了当前函数;

      在严格模式下,不能使 callee 和 caller 属性,会报错 TypeError;

            <script type="text/javascript">
                function fallingfactorial1 (x){//简单的阶乘
                    x = Math.round(Math.abs(x));
                    if(x <= 1){
                        return 1;
                    }else{
                        return x*fallingfactorial1 (x-1);//递归,这里需要写函数名,如果外面函数名改变,这里也得改,有点麻烦
                    }
                }
                console.log(fallingfactorial1(3));//6
    
                function fallingfactorial2 (x){//简单的阶乘
                    x = Math.round(Math.abs(x));
                    if(x <= 1){
                        return 1;
                    }else{
                        console.log(arguments.callee);//fallingfactorial2(x);
                        return x*arguments.callee(x-1);//使用arguments.callee,如果外面函数名改变,这里会自己去找的
                    }
                }
                console.log(fallingfactorial2(5));//120
                
                function fallingfactorial3 (x){//简单的阶乘
                    'use strict';//严格模式
                    x = Math.round(Math.abs(x));
                    if(x <= 1){
                        return 1;
                    }else{
                        return x*arguments.callee(x-1);//在严格模式下,不能使用callee属性,会报错TypeError
                    }
                }
    //            console.log(fallingfactorial3(5));//Uncaught TypeError
                
                function father(){
                    son();
                }
                
                function son(){
                    console.log(son.caller);
                    console.log(arguments.callee.caller); //callee和caller结合使用,寻找当前函数的引用
                }
                son();//null
                father();//function father(){son();}
                
                function test9(){
                    'use strict';//严格模式
                    console.log(test9.caller); //在严格模式下,不能使用caller属性,会报错TypeError
                }            
    //            test9();//Uncaught TypeError
            </script>
        </body>
  • 相关阅读:
    C++ 函数返回局部变量的std::move()的适用场景(转)
    Android 内存泄漏总结(转)
    android JNI调用(Android Studio 3.0.1)(转)
    Linux c —— opendir函数和readdir函数内涵及用法(转)
    理解Android编译命令(转)
    Linux内存管理(转)
    Android内存分析命令(转)
    关于跳板机穿透的文章 (未验证)
    windows下 git配置ssh
    转: Git远程操作详解 (阮一峰)
  • 原文地址:https://www.cnblogs.com/sspeng/p/6603733.html
Copyright © 2020-2023  润新知