zoukankan      html  css  js  c++  java
  • 深入浅出javascript(八)this、call和apply

    _________此篇日志属于重要记录,长期更新__________

    thiscallapply这三个是进阶JS的重要一步,需要详细的记录。

    ➢ this

    一、作为对象的方法调用。

    当函数作为对象方法被调用时,this指向该对象。

    首先,函数必须作为对象的方法。这句话很关键,因为函数的调用有很多种可能,在后面会展现。示例1-1

            var o = {
                name: 'o',
                get: function () {
                    return this.name;
                }
            }
            console.log(o.get());//输出'o'

    get方法是被对象o调用的,所以this指向o,这是没有异议的。

    现在把这个例子改下,示例1-2

            var o = {
                name: 'o',
                get: function () {
                    return this.name;
                }
            };
            var g = o.get;      //将o的get方法赋给g;
            console.log(g());   //输出空;

    o.get方法赋给g之后,现在这个方法g和原来的对象o已经没有关系了,因为g是全局的,所以它属于window的方法,结果导致方法内的this已经指向window,又,window没有定义name属性,所以输出为空。

    从这两个例子的对比可以看出,this是随机而动的,谁绑定,this就指向谁

    二、做为普通函数调用

    这里所说的普通函数调用主要是为了和狭隘的 ' 对象的方法调用 ' 来区别。因为无论函数怎么调用,它总属于一个对象,因为最外层总有一个window对象。

    如上例所示,将函数赋值给另一个变量,就是将这个函数从对象中 ’ 复制一份 ‘ 出来,结果变成window对象的一个方法,因此this指向window。

    示例2-1

    1.创建变量o,因为是全局的,所以内部的this为window,其内部的g也属于普通函数调用,因此也指向this。

    三、函数到底出现在哪儿?

    函数到底出现在哪里,说的是函数究竟出现在哪种地方,只有将出现的这几种地方弄明白,才能对函数做更深入的了解,总结如下:

    1 普通函数
    2 普通函数内部的普通函数
    3 对象内部
    4 对象内部的函数的内部

    ➢ 四种可能:

    普通函数

    this=window

    普通函数内部的普通函数

    this=window

    对象内部函数

    this=对象

    对象内部函数内部的普通函数

    this=window

    function f() {
      console.log(this);
    };

     

    function f() {
      function g() {
        console.log(this);
      }
    };

     

    var o = {
      get: function () {
        console.log(this);
      }
    };

     

    var o = {
      get: function () {
        function g() {
          console.log(this);
        }
      }
    };

    现在可以推断两条结论:

    一、凡是普通函数都指向window
    二、凡是对象调用都指向对象。(这里的对象是狭隘的对象,即自创建的对象)

    换句话说,凡遇到一个函数,首先两问:

    一、这个函数是普通函数吗?[如果是,则this=window]

    二、这个函数是被对象调用的吗?[如果是,则this=对象]

    ※ 回过头再看前面的一句话:当函数作为对象方法被调用时,this指向该对象,也就可以理解了。

    四、做为构造函数

    做为构造函数比较简单,this指定绑定的对象。仅示例:

            var F = function () {
                this.name = 'F';
            };
            var f=new F();

    ➢ apply和call

     一、概述

    apply就是函数调用,而调用的就是函数fn,也就是说执行fn( )。 apply后面是(对象,参数)。参数可以是数组,可以是类数组。

    所以理解这个apply就是记住两个点:

    1.调用函数fn.
    2.传入对象,如果传入的对象为null,则this=window

    apply概括:调用函数fn,fn需要依赖传入的对象来确定它内部的this到底指向谁。

    示例1-1

            window.name = 'window';
            function f() {
                console.log(this.name);
            }
            f.apply(null);  //输出'window'

    首次接触的时候有点点绕

    示例1-2

            function f() {
                console.log(this.name);
            }
            var o = {
                name: '对象o'
            };
            f.apply(o);

    二、作用

    1、改变this的指向

    首先,这个this指的是谁呢?肯定是fn内部的this。如果函数没有this,那又何谈改变this的指向呢。现在先做一个带有this的函数。

            function f() {
                console.log(this.name);
            }

    this是可以随意绑定的,这就是apply的作用,做个图示例一下:

            function f() {
                console.log(this.name);
            }
            var o = {
                name: 'o'
            };

    如上代码所示,f.apply(o),f内部的this绑定了对象o。

    2、借用其它对象的方法——继承

    这种继承是继承方法中的一种 [ 关于Javascript继承详细,参看记录 ],其实说起来更像是 ‘复制’。即:将父类中的属性复制一份到子类,代码2-1

            /***构造继承最简化的形式***/
    
            //父类
            function subClass() {
                this.name = 'subClass';
            }
            //子类
            function superClass() {
                subClass.call(this);
            }
            var o = new superClass();
            console.log(o.name);    //输出'subclass'

    ➢ 代码解析:

    子类构造函数使用父类.call,并将子类自己的this代入,结果就是将父类的属性 '复制' 了一份给子类。

     3、类数组的使用(重要!)

    补充于2018-10-23 20:12:51


    类数组一个比较常见的例子是arguments。这个东西像数组但又不是数组,如果采用一般的数组方法是不可行的,必须采用数组的call调用。

    示例如下:

    arguments.join(","),#这条语句希望将函数参数用","连接起来形成字符串,但是代码错误不能通过。这里采用Array原型方法调用:

    Array.prototype.join.call(arguments,",");

    这一条的应用比较常用且重要,也是采用call调用的一个比较独特的例子。

    4、

  • 相关阅读:
    平安夜前夜,我在上海沐恩堂度过
    吃匹萨的数学
    2004语录
    爱的罗曼斯
    转发: 上季度全球最佳短篇小说《最后一趟生意》
    一个人的元宵节
    超越纪念我的blog排名上升到第六位
    读《仆人》
    我的龟宝宝病了:( 谁来救救她?
    春晚
  • 原文地址:https://www.cnblogs.com/tinaluo/p/6677585.html
Copyright © 2011-2022 走看看