从getter返回的函数的`this`关键字的值


15

在以下示例中,我发现关键字的值意外:

let x = {
    z : 10 ,
    get func1() {
        return function(v) {
            console.log(this === v);
        }
    }
}


x.func1(x)

关键字的值是对象x,就像它是从该对象执行的一样,我希望只有具有关键字的get函数等于调用对象x

这个例子向我们展示了差异

let x = {
    func2() {
        return function(v) {
            console.log(this === v);
        }
    }
}

x.func2()(x);

在两个示例中,都是从对象x执行的是getter函数func1和作为对象的方法的func2,然后执行返回的函数。那么,为什么在第一个示例中值不等于全局对象而不是对象x


3
真的,这是一个非常有趣的问题。我从来没有这样的皱纹。
TJ Crowder

1
,就好像是从该对象执行的 ” –但它在该对象上执行的,就在附近:x.func1()
Bergi

Answers:


13

这是一个非常有趣的问题。

这是因为在属性访问结果后立即调用了该函数。因此,这些从根本上是等效的:

let x = {
    get func1() {
        return function(v) {
            console.log(this === v);
        };
    },
    func2(v) {
        console.log(this === v);
    }
};

x.func1(x);
x.func2(x);

在两种情况下:

  1. 读取属性的值,生成函数引用。
  2. 该函数作为同一属性访问表达式的一部分执行。

无论func1是访问器属性func2还是数据属性都无关紧要。重要的是使用读取属性产生的值。


1
我认为整个表达式将被评估为函数对象,然后执行。谢谢得到了
Kirollos Nasr

1
@KirollosNasr是的,但是,在表达式中, x.func1它将引用保留x为后续调用的上下文,这与x.func2()(从您的问题中得出)也算为一个函数但不是成员访问表达式相反。
Bergi

1
@Bergi-我想你的意思是x.func2()(x);
TJ Crowder

1
@TJCrowder是的,我指的是表达式中x.func1(x)x.func2()(x)
BERGI

1
@Bergi是的,它有一个棘手的部分。但是现在更加清楚了,感谢TJ Crowder和您
Kirollos Nasr
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.