TypeScript "this" 范围问题
TypeScript "this" issue with scope
我的代码片段:
class MyClass {
name = "MyClass";
// traditional method definition
getName1(){
return this.name;
}
// method defined as an arrow function
getName2 = () => {
return this.name;
}
// traditional method definition using a this parameter
getName3(this: MyClass){
return this.name;
}
}
const c = new MyClass();
const obj = {
name: "obj",
getName1: c.getName1,
getName2: c.getName2,
getName3: c.getName3
};
const g = c.getName3;
console.log(c.getName1());
// "MyClass" because this is called in the context of c
// using a traditional method definition getName1
console.log(c.getName2());
// "MyClass" because this is called in the context of c
// using an arrow function getName2
console.log(c.getName3());
// "MyClass" because this is called in the context of c
// using a traditional method definition getName3, having
// a this parameter that statically enforce the context of c
console.log(obj.getName1());
// "obj" because this is called in the context of obj
// using the MyClass traditional method definition getName1()
// and assigning it to obj's getName1 property
console.log(obj.getName2());
// "MyClass" because this is called in the context of obj
// using an arrow function getName2 and assigning it
// to obj's getName2 property, but which will preserve c's context
// nonetheless
console.log(obj.getName3());
// "obj" but why? Isn't the context of this enforced as that of MyClass? Shouldn't I get
// « The 'this' context of type 'obj' is not assignable to method's 'this' of type 'MyClass' »
console.log(g());
// Error, the 'this' context of type 'void' is not assignable to method's 'this' of type 'MyClass'.
// but isn't g declared in the global this context?
我的问题在评论中突出显示,但我还是将它们列如下:
- 为什么
console.log(obj.getName3());
显示"obj"
? this
的上下文是否与 MyClass
的上下文一样强制执行?我不应该得到类似的东西吗:
The 'this' context of type 'obj' is not assignable to method's 'this'
of type 'MyClass'
- 我知道
g
不是在 object/class 的上下文中声明的,而是在全局对象上下文中声明的,因此 this
应该指globalThis
?如果是这样,那为什么我会得到以下信息:
The 'this' context of type 'void' is not assignable to method's 'this'
of type 'MyClass'.
我认为打字稿将“外部”对象推断为 this,因此您可以从 obj.getName3() 获得“obj”,这没问题,因为它也与 class 匹配。它有名称 attr 和所有方法,所以没问题。
如果您将 obj.name 更改为 obj.noname(或 fn 名称之一),您将无法调用 obj.getName3(),因为 obj 不再与 class 匹配.
g() 也是如此。 g 的外部对象是 void 并且没有名称属性(和 fns),因此您会收到其他错误消息。
阅读更多:https://www.typescriptlang.org/docs/handbook/2/functions.html#declaring-this-in-a-function
我的代码片段:
class MyClass {
name = "MyClass";
// traditional method definition
getName1(){
return this.name;
}
// method defined as an arrow function
getName2 = () => {
return this.name;
}
// traditional method definition using a this parameter
getName3(this: MyClass){
return this.name;
}
}
const c = new MyClass();
const obj = {
name: "obj",
getName1: c.getName1,
getName2: c.getName2,
getName3: c.getName3
};
const g = c.getName3;
console.log(c.getName1());
// "MyClass" because this is called in the context of c
// using a traditional method definition getName1
console.log(c.getName2());
// "MyClass" because this is called in the context of c
// using an arrow function getName2
console.log(c.getName3());
// "MyClass" because this is called in the context of c
// using a traditional method definition getName3, having
// a this parameter that statically enforce the context of c
console.log(obj.getName1());
// "obj" because this is called in the context of obj
// using the MyClass traditional method definition getName1()
// and assigning it to obj's getName1 property
console.log(obj.getName2());
// "MyClass" because this is called in the context of obj
// using an arrow function getName2 and assigning it
// to obj's getName2 property, but which will preserve c's context
// nonetheless
console.log(obj.getName3());
// "obj" but why? Isn't the context of this enforced as that of MyClass? Shouldn't I get
// « The 'this' context of type 'obj' is not assignable to method's 'this' of type 'MyClass' »
console.log(g());
// Error, the 'this' context of type 'void' is not assignable to method's 'this' of type 'MyClass'.
// but isn't g declared in the global this context?
我的问题在评论中突出显示,但我还是将它们列如下:
- 为什么
console.log(obj.getName3());
显示"obj"
?this
的上下文是否与MyClass
的上下文一样强制执行?我不应该得到类似的东西吗:
The 'this' context of type 'obj' is not assignable to method's 'this' of type 'MyClass'
- 我知道
g
不是在 object/class 的上下文中声明的,而是在全局对象上下文中声明的,因此this
应该指globalThis
?如果是这样,那为什么我会得到以下信息:
The 'this' context of type 'void' is not assignable to method's 'this' of type 'MyClass'.
我认为打字稿将“外部”对象推断为 this,因此您可以从 obj.getName3() 获得“obj”,这没问题,因为它也与 class 匹配。它有名称 attr 和所有方法,所以没问题。
如果您将 obj.name 更改为 obj.noname(或 fn 名称之一),您将无法调用 obj.getName3(),因为 obj 不再与 class 匹配.
g() 也是如此。 g 的外部对象是 void 并且没有名称属性(和 fns),因此您会收到其他错误消息。
阅读更多:https://www.typescriptlang.org/docs/handbook/2/functions.html#declaring-this-in-a-function