箭头函数和 This
Arrow Functions and This
我正在试用 ES6 并希望在我的函数中包含一个 属性,就像这样
var person = {
name: "jason",
shout: () => console.log("my name is ", this.name)
}
person.shout() // Should print out my name is jason
然而,当我 运行 这个代码控制台只记录 my name is
。我做错了什么?
简短回答:this
指向最近的边界 this
- 在提供的代码中 this
在封闭范围内找到。
更长的答案:箭头函数
do not have this
, arguments
or other special names bound at all - 创建对象时,名称 this
在封闭范围内找到,而不是 person
对象。您可以通过移动声明更清楚地看到这一点:
var person = {
name: "Jason"
};
person.shout = () => console.log("Hi, my name is", this);
当翻译成 ES5 中箭头语法的模糊近似值时更加清晰:
var person = {
name: "Jason"
};
var shout = function() {
console.log("Hi, my name is", this.name);
}.bind(this);
person.shout = shout;
在这两种情况下,this
(对于 shout 函数)指向与定义 person
相同的作用域,而不是函数添加到时附加到的新作用域person
对象。
你不能使箭头函数那样工作,但是,正如@kamituel在中指出的那样,你可以利用 ES6 中较短的方法声明模式获得类似的 space 节省:
var person = {
name: "Jason",
// ES6 "method" declaration - leave off the ":" and the "function"
shout() {
console.log("Hi, my name is", this.name);
}
};
这里函数内部this的值是由箭头函数定义的地方决定的,而不是使用的地方。
所以 this
指的是 global/window 对象,如果没有包装在其他命名空间中的话
同意@Sean Vieira - 在这种情况下 this
绑定到全局对象(或者,如评论中所指出的,更一般地绑定到一个封闭范围)。
如果您想要更短的语法,还有另一个选择 - 增强的对象文字支持 属性 函数的短语法。 this
将按照您的预期进行绑定。见 shout3()
:
window.name = "global";
var person = {
name: "jason",
shout: function () {
console.log("my name is ", this.name);
},
shout2: () => {
console.log("my name is ", this.name);
},
// Shorter syntax
shout3() {
console.log("my name is ", this.name);
}
};
person.shout(); // "jason"
person.shout2(); // "global"
person.shout3(); // "jason"
问题是 (MDN)
An arrow function expression [...] lexically binds the this value.
Arrow functions capture the this value of the enclosing context.
因此,该函数中 this
的值将是您在其中创建对象文字的 this
的值。可能在非严格模式下是 window
,在严格模式下是 undefined
。
要修复它,您应该使用普通函数:
var person = {
name: "jason",
shout: function(){ console.log("my name is ", this.name) }
}
person.shout();
接受的答案非常好、简洁明了,但我会详细说明肖恩维埃拉所说的话:
Arrow functions do not have
this arguments or other special names bound at all.
因为箭头函数没有 "this",它使用父级的 "this"。 "this" 总是指向父对象,person 对象的父对象是 Window(如果您在浏览器中)。
为了证明这一点 运行 在您的控制台中:
var person = {
name: "Jason",
anotherKey: this
}
console.log(person.anotherKey)
您将获得 Window 对象。
我发现这是一种非常有用的思考方式。这不是完整的故事,因为对象文字的 "this" 是什么是另一个讨论。
我正在试用 ES6 并希望在我的函数中包含一个 属性,就像这样
var person = {
name: "jason",
shout: () => console.log("my name is ", this.name)
}
person.shout() // Should print out my name is jason
然而,当我 运行 这个代码控制台只记录 my name is
。我做错了什么?
简短回答:this
指向最近的边界 this
- 在提供的代码中 this
在封闭范围内找到。
更长的答案:箭头函数
do not have this
, arguments
or other special names bound at all - 创建对象时,名称 this
在封闭范围内找到,而不是 person
对象。您可以通过移动声明更清楚地看到这一点:
var person = {
name: "Jason"
};
person.shout = () => console.log("Hi, my name is", this);
当翻译成 ES5 中箭头语法的模糊近似值时更加清晰:
var person = {
name: "Jason"
};
var shout = function() {
console.log("Hi, my name is", this.name);
}.bind(this);
person.shout = shout;
在这两种情况下,this
(对于 shout 函数)指向与定义 person
相同的作用域,而不是函数添加到时附加到的新作用域person
对象。
你不能使箭头函数那样工作,但是,正如@kamituel在
var person = {
name: "Jason",
// ES6 "method" declaration - leave off the ":" and the "function"
shout() {
console.log("Hi, my name is", this.name);
}
};
这里函数内部this的值是由箭头函数定义的地方决定的,而不是使用的地方。
所以 this
指的是 global/window 对象,如果没有包装在其他命名空间中的话
同意@Sean Vieira - 在这种情况下 this
绑定到全局对象(或者,如评论中所指出的,更一般地绑定到一个封闭范围)。
如果您想要更短的语法,还有另一个选择 - 增强的对象文字支持 属性 函数的短语法。 this
将按照您的预期进行绑定。见 shout3()
:
window.name = "global";
var person = {
name: "jason",
shout: function () {
console.log("my name is ", this.name);
},
shout2: () => {
console.log("my name is ", this.name);
},
// Shorter syntax
shout3() {
console.log("my name is ", this.name);
}
};
person.shout(); // "jason"
person.shout2(); // "global"
person.shout3(); // "jason"
问题是 (MDN)
An arrow function expression [...] lexically binds the this value.
Arrow functions capture the this value of the enclosing context.
因此,该函数中 this
的值将是您在其中创建对象文字的 this
的值。可能在非严格模式下是 window
,在严格模式下是 undefined
。
要修复它,您应该使用普通函数:
var person = {
name: "jason",
shout: function(){ console.log("my name is ", this.name) }
}
person.shout();
接受的答案非常好、简洁明了,但我会详细说明肖恩维埃拉所说的话:
Arrow functions do not have this arguments or other special names bound at all.
因为箭头函数没有 "this",它使用父级的 "this"。 "this" 总是指向父对象,person 对象的父对象是 Window(如果您在浏览器中)。
为了证明这一点 运行 在您的控制台中:
var person = {
name: "Jason",
anotherKey: this
}
console.log(person.anotherKey)
您将获得 Window 对象。
我发现这是一种非常有用的思考方式。这不是完整的故事,因为对象文字的 "this" 是什么是另一个讨论。