• 箭头函数中的this


    普通函数中的this:

    1.this总是代表它的直接调用者, 例如 obj.func ,那么func中的this就是obj
    2.在默认情况(非严格模式下,未使用 'use strict'),没找到直接调用者,则this指的是 window
    3.在严格模式下,没有直接调用者的函数中的this是 undefined
    4.使用call,apply,bind(ES5新增)绑定的,this指的是 绑定的对象

    首先了解一下作用域链:

    当在函数中使用一个变量的时候,首先在本函数内部查找该变量,如果找不到则找其父级函数,

    最后直到window,全局变量默认挂载在window对象下

    箭头函数有几个使用注意点。

    (1)函数体内的this对象,就是定义时所在的对象,而不是使用时所在的对象。

    (2)不可以当作构造函数,也就是说,不可以使用new命令,否则会抛出一个错误。

    (3)不可以使用arguments对象,该对象在函数体内不存在。如果要用,可以用 rest 参数代替。

    (4)不可以使用yield命令,因此箭头函数不能用作 Generator 函数。

    上面四点中,第一点尤其值得注意。this对象的指向是可变的,但是在箭头函数中,它是固定的。

    箭头函数中的this

    默认指向在定义它时,它所处的对象,而不是执行时的对象, 定义它的时候,可能环境是window

    1.全局变量默认挂载在window对象下

    <script>
      var aa = 2;
      alert(window.aa);
      (function () {
        aa = 3;
      })();
      console.log(window.aa);
    </script>
    

    2.在普通函数中,this指向它的直接调用者;如果找不到直接调用者,则是window

    示例1:

    <script>
      function test() {
        console.log(this);
      }
      test();
    </script>
    

    结果是: window
    原因: test()是一个全局函数,也就是说是挂在window对象下的,所以 test()等价于 window.test() ,所以此时的this是window
    示例2:

    <script>
      var obj = {
        say: function () {
          setTimeout(function () {
            console.log(this)
          });
        }
      }
      obj.say();
    </script>
    

    结果是: window
    匿名函数,定时器中的函数,由于没有默认的宿主对象,所以默认this指向window

    问题: 如果想要在setTimeout中使用这个对象的引用呢?

    用一个 变量提前把正确的 this引用保存 起来, 我们通常使用that = this, 或者 _this = this来保存我们需要的this指针!

    <script>
      var obj = {
        func: function() {},
        say: function () {
          var that = this;   //此时的this就是obj对象
          setTimeout(function () {
            console.log(this)
            that.func()
          });
        }
      }
      obj.say();
    </script>
    

    示例3:

    window.val = 1;
      var obj = {
        val: 2,
        dbl: function () {
          this.val *= 2;
          val *= 2;
          console.log(val);
          console.log(this.val);
        }
      };
      // 说出下面的输出结果
      obj.dbl();
      var func = obj.dbl;
      func();
    

    结果是: 2 4 8 8
    val变量在没有指定对象前缀,默认从函数中找,找不到则从window中找全局变量

    即 val *=2 就是 window.val *= 2

    this.val默认指的是 obj.val ;因为 dbl()第一次被obj直接调用

    func() 没有任何前缀,类似于全局函数,即 window.func调用,所以

    第二次调用的时候, this指的是window, val指的是window.val

    第二次的结果受第一次的影响

    3.在严格模式下的this

    <script>
      function test() {
        'use strict';
        console.log(this);
      }
      test();
    </script>
    

    结果是: undefined

    4.箭头函数中的 this

    <script>
      var obj = {
        say: function () {
          setTimeout(() => {
            console.log(this)
          });
        }
      }
      obj.say(); // obj
    </script>
    

    此时的 this指的是定义它的对象, obj,而不是 window!

    示例(多层嵌套的箭头函数):

    <script>
      var obj = {
        say: function () {
          var f1 = () => {
            console.log(this); // obj
            setTimeout(() => {
              console.log(this); // obj
            })
          }
          f1();
        }
      }
      obj.say()
    </script>
    

    因为f1定义时所处的函数 中的 this是指的 obj所以不管有多层嵌套,都是 obj

    示例(复杂情况: 普通函数和箭头函数混杂嵌套)

    <script>
      var obj = {
        say: function () {
          var f1 = function () {
            console.log(this);    // window, f1调用时,没有宿主对象,默认是window
            setTimeout(() => {
              console.log(this); // window
            })
          };
          f1();
        }
      }
      obj.say()
    </script>
    

    结果: 都是 window,因为 箭头函数在定义的时候它所处的环境相当于是window所以在箭头函数内部的this函数window

    示例(严格模式下的混杂嵌套)

    <script>
      var obj = {
        say: function () {
          'use strict';
          var f1 = function () {
            console.log(this); // undefined
            setTimeout(() => {
              console.log(this); // undefined
            })
          };
          f1();
        }
      }
      obj.say()
    </script>
    

    结果都是undefined

    说明: 严格模式下,没有宿主调用的函数中的this是undefined!!!所以箭头函数中的也是undefined!

    总结:

    使用箭头函数,可以让我们解决一些在匿名函数中 this指向不正确的问题;但是要注意在和普通函数混合的时候,this的指向可能是window !

  • 相关阅读:
    DataGrid 应用合集
    [转]UBB C#完全版
    IE 7中的快捷键
    DataGrid 单击变色,鼠标经过变色 部分代码
    17种正则表达式
    单无格内强制换行
    图片上传,并自动生成缩略图!
    layout_weight学习心得
    android 手势
    java陷进一
  • 原文地址:https://www.cnblogs.com/laijun/p/7402135.html
Copyright © 2020-2023  润新知