zoukankan      html  css  js  c++  java
  • 第五章 引用类型>Function类型

    Function类型

    每个函数都是Function类型的实例,与其他引用类型一样具有属性和方法。

    函数声明语法定义:

    function sum(num1, num2) {
        return num1+num2;
     }

    函数表达式定义:

    var sum = function(num1, num2) {
                    return num1 + num2;
               };

    由于函数是对象,因此函数名是一个指向函数对象的指针。不会与某个函数绑定。

    function sum(num1, num2) {
        return num1 + num2;
      }
    console.log(sum(10, 10));
    //20
    
    var anotherSum = sum;                 //将函数的值赋给anotherSum,不带圆括号的函数名访问的是函数指针而非调用函数。
    console.log(anotherSum(10, 10));   //sum和anotherSum指向同一个函数
    //20 
    
    sum = null;                                   //就算把sum清空; anotherSum还是可以调用, 清空的只是函数名的指针而已,ahotherSum的指针没有被清空
    console.log(anotherSum(10, 10));
    //20

    函数没有重载

    同名函数只能存在一个,后面覆盖前面的;

    funcition addSomeNumber(num) {
                return num+100;
         }
    
    function addSomeNumber(num) {
               return num + 200;
          }
    
    var result = addSomeNumber(100);
    console.log(result);
    //300
    
    //上面的代码和下面的基本没有区别
    var  addSomeNumber = function(num) {
                   return num +100;
             };
    
    
    var  addSomeNumber = function(num) {
                   return num +200;
             };

    函数声明与函数表达式

    函数声明:     解析器率先读书函数声明。函数声明被提升到代码的顶部,使在执行任何代码之前可用。

    console.log(sum (10, 10));
    function sum (num1, num2) {
             return num1 + num2;
       }
     
    // 20  对代码求值时JS引擎再第一遍声明函数并将他们放到源代码的顶部。

    函数表达式:  只有变量名被提前了, 而变量名知识一个指向函数对象的一个指针。函数体和函数声明依然在变量所在行执行。

    console.log(sum1(10, 10));
    var sum1 = function(num1, num2) {
             return num1 + num2;
            };
    // Uncaught TypeError: sum1 is not a function(…)
    
    //在执行到函数所在的语句之前,变量sum并没有保存对函数的引用.变量被提升到了顶部,赋值语句还在原来的地方进行。第一行代码就会导致 Uncaught TypeError;根本不会执行到下一行

    作为值的函数

    function callSomeFunction(someFunction, someArguments) {
             return someFunction(someArguments); 
            }
    
    function getGreeting(name) {
       return "hello!" + name;
     }
    
    var result2 = callSomeFunction(getGreeting, "zhangsan");
    // 没有使用圆括号的getGreeting,只是获得了getGreeting指向的那个函数对象的指针,并不是立即调用函数,返回结果。
    

    console.log(result2); // hello!zhangsan

    从一个函数中返回另外一个函数。

    function createComparisonFunction(propertyName) {
             return function (object1, object2) {
                    var value1 = object1[propertyName];
                    var value2 = object2[propertyName];
                   
                    if(value1 < value2) {
                           return -1;
                       } else if (value1 > value2) {
                         return 1; 
                       }else {
                         return 0;
                       }
                   };
              }
    
    var data = [{name: "Zachary", age: 28},{name: "Nicholas", age: 29}];
    //创建一个包含2个对象的数组data。每个对象都有一个name属性,和age属性
    
    data.sort(createComparisonFunction("name"));
    //调用写好的排序函数,把name属性当做排序函数的参数传递进去 console.log(data[
    0].name); data.sort(createComparisonFunction("age")); console.log(data[0].name); // Nicholas // Zachary

    函数内部属性

    函数内部俩个特殊的对象:

    arguments: 类数组对象,包含着传入函数中的所有参数。

    aruguments还有一个callee的属性;

    callee: 该属性是个指针,指向拥有这个arguments对象的函数。

    function factorial(num) {
             if(num<=1) {
                   return 1;
                } else {
                     return num*arguments.callee(num-1);
                }
           }
    var trueFactorial = factorial;
    
    factorial = function() { return 0;};
    //factorial的指针被修改
    console.log(factorial(5));     
    // 0
    console.log(trueFactorial(
    5));
    //120 trueFactorial的指针依然指向的是之前的阶乘函数对象。

    this: 引用的是函数 据以执行的环境对象,或者也可以说是this值(在网页的全局作用域调用this对象引用的是WINDOW);

    window.color = "red";
    var o = { color: "blue" };
    
    function sayColor() {
        console.log(this.color);
       // 由于函数是全局作用域定义的函数,this.color = window.color
      }
    sayColor();
    o.sayColor = sayColor;  //相当于用匿名函数的形式把函数赋给变量,sayColor 里面的this引用对象的是o 
    o.sayColor();
    // red
    // blue

    caller:保存这调用当前函数的函数的引用;如果是全局作用域调用调用当前函数,值为null;

    function outer() {
        inner();
       }
    function inner(){
        console.log(inner.caller);
      //可以用arguments.callee.caller。是一样的效果
      }
    outer();
    // outer() {  inner();  }

    函数的属性和方法

    length:        函数希望接受的命名参数的个数;

    prototype:  保存所有实例和方法的真正所在。

    函数包含2个非继承来的方法:apply()和call(),作用是在特定作用域中调用函数,设置函数体内的this对象的值。

    apply(): 接受俩个参数, 第一个参数是再其运行函数的作用域,第二个参数,可以是数组,也可以是Array的实例,也可要是arugments的对象。

    function sum2(num1, num2) {
             return num1 + num2;
         }
    
    function callSum1(num1, num2) {
             return sum2.apply(this, arguments);
              //截获sum2函数并当做返回值返回
    //这里 的this指的window。因为sum2是全局作用域的函数 this = window.sum2
    } function callSum2(num1, num2) { return sum2.apply(this,[num1, num2]); } console.log(callSum1(10, 10)); console.log(callSum2(10, 10)); // 20 // 20

    call():和apply的作用一样。第二个接受的参数方式不同, 递给call()的参数必须逐个列举出来。

    function sum(num1, num2) {
              return num1 + num2;
         }
    function callSum(num1, num2) {
              return sum.call(this, num1, num2);
       }
    
    console.log(callSum(10, 10));

    call()和apply()最大的作用扩充函数赖以运行的作用域

    window.color = "red";
    var o = { color: "blue" };
    
    function sayColor() {
         console.log(this.color);
       }
    
    sayColor();
    sayColor.call(this);
    sayColor.call(window);
    sayColor.call(o);
    // red
    // red
    // red
    // blue

    bind():  这个方法会创建一个函数实例,this值 会被绑定到传给bind()函数的值。

    window.color = "red";
    var o = { color: "blue" };
    
    function sayColor() {
         console.log(this.color);
       }
    var objectSayColor = sayColor.bind(o);
    //把this的值设置为o
    objectSayColor();
    // blue
  • 相关阅读:
    MongoDB 时间截取、字符串截取、拼接(时间戳、字符串等)
    ClickHouse 参数配置
    C++函数调用栈的变化分析
    WPF中为button添加快捷键(ShortCut)的方法
    vscode中一些好用的插件介绍
    剑指Offer 2. 青蛙跳台阶问题
    切片Slice的使用
    剑指Offer 1. 斐波那契数列
    match_parent和wrap_content的区别
    字节流、字符流
  • 原文地址:https://www.cnblogs.com/zhangbaihua/p/5564513.html
Copyright © 2011-2022 走看看