箭头函数与 setTimeout 中的 es5 函数的作用域



我正在试验这个和箭头函数。 在 setTimeout 中箭头函数的词法范围方面遇到了一些麻烦。

方法将此作为狗对象返回。为什么它不占用全局对象的作用域,因为箭头函数在 setTimeout 方法内?有趣的是,whatIsThis 方法返回超时对象而不是全局对象。我也对此感到困惑。

const dog = {
name: 'fluffy',
type: 'dog',
sound: 'woof!',
makeSound: function() {
setTimeout(() => {
console.log("makeSound", this)
}, 1000)
},
whatIsThis: function() {
setTimeout(function() {
console.log("whatisthis", this)
}, 1000)
}
}
dog.makeSound() // returns dog obj
dog.whatIsThis() // returns Timeout obj
setTimeout(() => {
console.log("global", this)
}, 1000) // returns global obj

为什么它不占用全局对象的作用域,因为箭头函数在 setTimeout 方法内?

回调不在setTimeout函数的"内部"。它作为参数传递给setTimeout函数。

请考虑以下等效代码:

const dog = {
name: 'fluffy',
type: 'dog',
sound: 'woof!',
makeSound: function() {
const cb = () => console.log("makeSound", this);
setTimeout(cb, 1000)
},
}

此代码的行为完全相同。唯一的区别是回调函数在传递给setTimeout之前先分配给变量。

这应该证明箭头函数不是"在"setTimeout,而是在makeSound内部。箭头函数以词法方式解析this,就像任何其他变量一样。因此,我们必须找出makeSound内部this的价值是什么。为了找出答案,我们必须看看该方法是如何调用的。由于它被称为dog.makeSound()this指的是dog

箭头函数声明的作用域是围绕它的函数的作用域(dog.makeSound(,而不是箭头函数传递到的函数。

不管你怎么称呼dog.makeSound()thismakeSound函数内部指的是dog,因此它在箭头函数内部也是如此。

// no matter what the surrounding is ...
const that = this;
/*no matter whats here*/(() => {
console.log(that === this); // this will always be true
})();

有趣的是,whatIsThis 方法返回超时对象而不是全局对象。我也对此感到困惑。

我也是。这种行为很奇怪,您确定您没有误解控制台输出吗?

最新更新