• js函数知识


    1、函数基本知识

    通过函数可以封装任意条语句,在任何地方调用,js中用function关键字来声明,

            //基本格式,函数名,传递参数,代码块
            function functionName(arg0,arg1,arg2,……,argN){
                 statements
            }
            
            //实例
            function sayHi(name,message){
                  console.log("hello "+name+","+message)
            }
            sayHi("double","how are you")    //普通的函数名调用函数
    
            function sum(numb1,numb2){
                 return numb1+numb2;
                 console.log("find me ?")    //因为之前有return,所以不会再执行
            }
            var result=sum(1,2);             //声明变量的做法来调用函数
    
    
            function summ(numb1,numb2){
                  return;                    //return可以不带任何返回值,这时候会返回undefined
                  console.log("hello")
            }
    
            function diff(numb1,numb2){      //一个简单的比较函数
                 if(numb1<numb2){
                      return numb2-numb1;
                 }
                 else{
                      return numb1-numb2;
                 }
            }

    1.1理解参数

    js中的参数在其内部使用一个数组表示,所以无论参数的数据类型,个数都没关系,而且参数也不一定会用上的。

    函数体内可以通过arguments对象访问到参数的数组,从而获得每一个参数。arguments对象和数组相似,可以中括号表示,有length;

    参数名不是必须的,为了方便而已,也可以通过arguments[0]访问到

            function change(){
                console.log(arguments.length)
            }
            var zero=change()         //0      可以通过length来展现
            var one=change("one")     //1
            var two=change("two",2)   //2
            
            //没有参数名
            function doAdd(){
                if(arguments.length==1){
                    console.log(arguments[0]+10);
                }else if(arguments.length==2){
                    console.log(arguments[0]+arguments[1])
                }
            }
            doAdd(1)      //11
            doAdd(1,2)    //3
    
            //有参数名
            function anotherAdd(num1,num2){
                if(arguments.length==1){
                     console.log(num1+10);
                }else if(arguments.length==2){
                     console.log(num1+num2)
                }
            }
            anotherAdd(1)    //11
            anotherAdd(1,2)  //3
    
            function again(num1,num2){
                arguments[1]=10;
            //这里num2的值也就变成10,arguments的值与对应命名参数的值保持同步,内存空间还是独立的;没有传递值得命名参数为undefined          
                console.log(arguments[0]+num2)
            }

    1.2没有重载

    所谓的没有重载就是说,不可以为函数两个定义,因为js的参数是数组,没有签名,做不到真正的重载。两个相同的函数则以后一个为准。

    Function类型

    也是引用类型,每个函数就是Function类型的实例,都与其他引用类型具有相同的属性和方法。函数为对象,所以函数名只是指向函数对象的指针

    声明变量有两种方式。看例子吧。

          function sum(num1,num2){     //函数声明来定义函数
                return num1+num2
          }
    
          var sum=function(num1,num2){  //函数表达式定义函数
                return num1+num2
          }
    
          //函数名仅仅为指针;所以也能理解上面所说的函数没有重载
          function one(num1,num2){
               return num1+num2
          }
          var two=one
          var one=null
          console.log(two(1,2))    //3  即使one为null

    函数声明和函数表达式之间的相爱相杀

    解析器对他们两个态度可是不同的

    对于函数声明,解析器会优先读取,对其有个函数声明提升的过程(function declaration hoisting)

    对于函数表达式,解析器可就不会优先了,只有读取到其,才会被解释执行

          console.log(sum(1,2))        //3
          function sum(num1,num2){     
                return num1+num2
          }
    
          console.log(another(1,2))    //another is not a function
          var another=function(num1,num2){
                return num1+num2
          }

    当然还有构造函数法,不推荐使用,导致代码的二次解析,一次是常规js的,一次是构造函数的

    也就是函数可以作为值传参

         function sum(someFunction,value){        //基本的函数中的嵌套
                 return someFunction(value)
         }
    
         function multiplys(num){                 //内部的函数
                return num*num
         }
    
         console.log(sum(multiplys,2))            //调用函数,访问内部函数的指针,不需要()调用

    利用作为值得函数,可以按照某一属性对数组进行排序

         function compare(value){                 //想要通过比较obj的属性,这里的value只是参数,没有被实例化;而在简单的数组中都已经被实例化了
               return function(obj1,obj2){
                  var value1=obj1[value]
                  var value2=obj2[value]
                  return value1-value2
               }
         }
    
         var data=[{name:"double",age:24},{name:"zom",age:23},{name:"mike",age:32}]
         data.sort(compare("age"))
         console.log(data)         //23,,24,32来排序

    2、函数内部的属性

    在函数的内部,一般有两个对象

    this对象:this引用的是函数执行的环境对象,即this值(在全局环境中,this则代表的是window)

    arguments对象:类数组对象,保存函数参数;有个callee属性,此属性是个指针,指向拥有arguments对象的函数

    ES5规定了另个一个函数对象的属性caller,保存着调用当前函数的函数引用,在全局作用域中调用当前函数则为null

         //递归函数
         function sum(num){
              if(num<=1){
                  return 1
              }
              else{
                  return num*arguments.callee(num-1)     //消除紧紧耦合,保证完成递归函数,所以用callee属性
              }
         }
         var summ=sum;
         sum=null
         console.log(summ(10))
    
    
        //this
        window.color="red"
    
        function sayColor(){
             console.log(this.color)
        }
    
        sayColor()                    //red
    
        var another={color:"blue"}   
        another.putColor=sayColor     //函数名只是个指针
        another.putColor()            //blue
    
    
      //函数对象属性caller
      function outer(){
          inner()
      }
     /*  function inner(){
          console.log(inner.caller)
      }*/
      function inner(){
          console.log(arguments.callee.caller)    //减少耦合
      }
      outer()             //outer()函数

    3、函数的属性和方法

    每个函数有两个属性

    length属性:表示函数的参数名个数

    prototype属性:保存引用类型所有实例方法,不可枚举,用for-in无法实现

    每个函数都包含两个非继承的方法;都是在特定的作用域中调用函数,实际等于设置函数体内this对象的值

    apply()方法:接受两个参数,一为在其中运行函数的作用域,一为参数数组(Array的实例或者arguments对象)

    call()方法:接受的第一个参数是this值没变化,第二个不是数组了,直接传递给参数即可,看例子吧

       function sum(num1,num2){
           return num1+num2
       }
    
       function oneSum(num1,num2){
           return sum.apply(this,arguments)         //arguments对象
       }
       function twoSum(num1,num2){
           return sum.apply(this,[num1,num2])       //数组
       }
    
       console.log(oneSum(1,2))
       console.log(twoSum(1,2))
    
       function three(num1,num2){
           return sum.call(this,num1,num2)          //参数直接传递
       }
       console.log(three(1,2,3))   
      
      //apply()和call()方法可以扩充函数的作用域
      window.color="red"
      var one={color:"red"}
    
      function sayColor(){
          console.log(this.color)
      } 
      sayColor()                  //red
    
      sayColor.call(this)         //red
      sayColor.call(window)       //red
      sayColor.call(one)          //blue   这里的作用域为one中的了,不需要再将函数放到one中等操作

    ES5规定还规定一个方法bind(),创建一个函数实例,其this值被绑定到传给bind()函数的值,

      window.color="red"
      var one={color:"blue"}
    
      function sayColor(){
          console.log(this.color)
      }
    
      var another=sayColor.bind(one)     //ES5的函数方法,创造一个函数实例了,并且绑定的this值传递给函数了
      another()                          //blue
  • 相关阅读:
    Android学习---- 十月
    第17章 使用PHP和MySQL实现身份验证
    第13章 MySQL高级编程
    第12章 MySQL高级管理
    第11章 使用PHP从Web访问MySQL数据库
    第10章 使用MySQL数据库
    第9章 创建Web数据库
    第5章 代码重用与函数编写
    NOIP模拟赛-奶牛晒衣服(dry)
    BZOJ1008 /乘法原理+快速幂 解题报告
  • 原文地址:https://www.cnblogs.com/iDouble/p/8372468.html
Copyright © 2020-2023  润新知