JavaScript你可能不知道的JavaScript 前端开发那些事儿

当箭头函数被普通函数包裹

2020-11-15  本文已影响0人  小遁哥

春暖花开,万物复苏,又到了看面试题的时候...

很多文章讲述箭头函数this的指向,都提到了定义二字,是容易误导人的,MDN中这样解释

箭头函数不会创建自己的this,它只会从自己的作用域链的上一层继承this。

    window.oop = 'window';
    let obj = {
      oop: 'obj',
      print: function () {
        setTimeout(function () {
          console.log(this.oop);
        });
      },
    };
    obj.print();

此时会输出"window",普通函数的this是谁调用指向谁,setTimeout作为宏任务,是在在全局环境下执行的。

    window.oop = 'window';
    let obj = {
      oop: 'obj',
      print: function () {
        setTimeout(() => {
          console.log(this.oop);
        });
      },
    };
    obj.print();

此时则会输出"obj",因为 obj.print使得print函数的this指向obj对象,被setTimeout里的箭头函数继承

    window.oop = 'window';
    let obj = {
      oop: 'obj',
      print: function () {
        setTimeout(() => {
          console.log(this.oop);
        });
      },
    };
    const print = obj.print;
    print();

此时输出的是windowprint();是在全局环境下调用的,所以setTimeout里的箭头函数继承
window


React 为啥要绑定this
在绑定事件函数时

<button onClick={this.handleClick} >
</button>

其实类似于(严格模式)

const print = obj.print;
print();

下面的例子解释了为什么箭头函数解决了this的指向问题


    window.oop = 'window';
    let obj = {
      oop: 'obj',
      print: () => {
        setTimeout(() => {
          console.log(this.oop);
        });
      },
    };
    obj.print();

输出"window",尽管通过obj.print(),但是此时print中的this是继承上一层的

箭头函数的出现是为了替普通函数分忧的,不是替代,MDN解释如下

箭头函数表达式的语法比函数表达式更简洁,并且没有自己的this,arguments,super或new.target。
箭头函数表达式更适用于那些本来需要匿名函数的地方,并且它不能用作构造函数。

看一个防抖的例子

function debounce(func, delay) {
      let isFirstTime = true;
      let timer;
      return function (...args) {
        if (isFirstTime) {
          func.apply(this, args);
          isFirstTime = false;
        } else {
          clearTimeout(timer);
          timer = window.setTimeout(() => {
            func.apply(this, args);
          }, delay);
        }
      };
    }
    function sayHi() {
      console.log(this);
    }
    const oopBtn = document.getElementById('oop');
    oopBtn.addEventListener('click', debounce(sayHi, 500));

如果将return返回的写成箭头函数,sayHithis将指向window

上一篇 下一篇

猜你喜欢

热点阅读