var f = function() {
this.x = 5;
(function() {
this.x = 3;
})();
console.log(this.x);
};
f.call(f);
f();
f.call();
将var f
运行为f.call(f)
,输出5
。当以f()
或f.call()
的身份运行时,输出为3
。
在每种情况下会发生什么?内部函数的this
指的是什么?
答案 0 :(得分:14)
首先,您要调用该函数。在函数内部,函数本身即f
被设置为this
。因此,在第一个示例中,this.x = 5;
在函数上设置属性x
。
调用内部函数this
时会引用window
对象,因此this.x = 3;
会更改窗口对象的x
属性。
在此处记录console.log(this.x);
时,将记录设置为功能属性的相同属性x
。
在第二个示例中,外部函数内部的this
引用了window
,因此当评估this.x = 3;
时,window.x
变成3
。由于this
在外部函数中引用了window
,因此console.log(this.x);
记录了window.x
的{{1}}
整个讨论的结论是,如果没有参数传递给3
,那么将自动绑定call()
对象。根据{{3}}
thisArg
可选的。此值提供给函数调用。请注意,这可能不是该方法看到的实际值:如果该方法是非严格模式下的函数,则 null和undefined将被全局对象替换,并且原始值将转换为对象。
请参见下面的代码段。
window
答案 1 :(得分:6)
如果没有特定的上下文,则this
将是window
。您的内部函数始终在没有上下文的情况下运行,因此会将window.x
设置为3。如果您调用f()
,它也会以this
为window
的身份运行,因此记录了3.
如果您执行f.call(f)
,则this
将是f
函数对象,并且其x
属性将设置为5。
f.call(f)
console.log(
f.x, // 5
window.x // 3
);
如果尚不清楚,建议您使用debugger逐步解决。
答案 2 :(得分:2)
调用带有自身引用的f
时,它将功能上的x
属性设置为5,并且内部匿名函数的this
引用窗口,因此将window.x设置为3。在匿名函数之外,this
仍引用函数f
,因此console.log(this.x)输出5。
使用f()
或f.call()
调用f时,函数f及其内部的匿名函数将this
引用设置为window
(默认值),依此类推在匿名函数内部或外部更改this.x
的值会影响输出结果。
如果您在console.f和内部匿名函数中分别记录this
的值,则可以清楚地看到这一点。
var f = function() {
console.log("This inside function f:", this.toString());
this.x = 5;
(function() {
console.log("This inside anonymous inner function:", this.toString());
this.x = 3;
})();
console.log(this.x);
};
console.log("calling function x with this set to itself");
f.call(f);
console.log("---------------")
console.log("invoking function x with brackets ()")
f();
console.log("---------------")
console.log("calling function x without setting this context")
f.call();
console.log("---------------")
答案 3 :(得分:1)
在其他答案中,如果您想要可预测的行为,则至少可以使用两种方法。
方法1 :(关闭)
var f = function() {
this.x = 5;
var that = this;
(function() {
that.x = 3;
})();
console.log(this.x);
};
f.call(f); // 3
f(); // 3
f.call(); // 3
方法2 :(箭头功能)
var f = () => {
this.x = 5;
(function() {
this.x = 3;
})();
console.log(this.x);
};
f.call(f); // 3
f(); // 3
f.call(); // 3
答案 4 :(得分:0)
“此”关键字指的是当前代码正在其中执行的上下文对象。在任何函数之外,它均指代全局对象。
通过使用call()
,apply()
函数的值可以从一个上下文传递到另一个上下文。
f
,this.x
指5。因此答案是
打印为5。this
的执行上下文称为3。所以它
打印为3。3
作为输出。