"this"函数中的上下文



在下面的代码中,我无法理解一些关于this的事情

function Stack() {
let items = [];
push = function(element){
items.push(element);
};
this.pop = function(){
return items.pop(); // removes and returns the element.
};
}
let stk= new Stack();
stk.push(); // 1 
stk.pop(); //  no error
  1. 抛出stk.push不是一个函数。 为什么 ? 为什么缺乏this会阻止推送方法。
  2. 为什么一定要new Stack(),为什么不能let stk= Stack()识别函数内部的方法?

由于我正在实例化 Stack 函数,无论方法是否用this声明,stkvar 都应该能够访问函数,不是吗?

让我们看两个例子:

push = function() { /*...*/ }

var push = function() { /*...*/ }

在第一个中,push是一个全局变量。 所以我们没有定义任何类似的东西Stack.push它是push. 所以文你做:

push();

它被执行了,当然失败了!

在第二个中,变量的作用域在本地,这意味着它只能在函数内部使用Stack

因此,在这种情况下,推送在 Stack 之外的任何地方都是未定义的。

没有定义pushStack.pushstk.push

现在让我们看看其他选项:

this.push = function() { /*...*/ }

这将定义当前对象的字段push

让我们澄清一下:

let Stack = function() {
this.push = function() { console.log("Hello!"); }
console.log(this);
};
Stack();

所以我们得到的是:

窗口 {框架: 窗口, 帖子消息: ƒ, 模糊: ƒ, 焦点: ƒ,

关闭: ƒ, ...}

等什么?这意味着函数的上下文(this)是Window对象。 所以在这种情况下(如果我们在浏览器中工作),我们再次定义了全局 可变push

let Stack = function() {
this.push = function() { console.log("Hello!"); }
};
Stack();
push();

输出

你好!

所以现在要拯救的是new关键词。 基本上Mozilla文档说:

当执行新的 Foo(...) 代码时,会发生以下情况:

创建一个新对象,继承自 Foo.prototype。 构造函数 Foo 使用指定的参数调用,并且 这绑定到新创建的对象。 新Foo相当于新Foo(), 即,如果没有指定参数列表, Foo 的调用没有参数。

构造函数返回的对象将成为整个新表达式的结果。如果构造函数未显式返回对象,则改用在步骤 1 中创建的对象。

(通常构造函数不返回值,但如果它们想要重写正常的对象创建过程,则可以选择这样做。

就是这样! 新关键字将this绑定到newly created object

所以当我们执行

new Stack()

this关键字是指我们创建的对象!这就是为什么当我们分配时

this.push = /* Something */

可以理解为以下代码:

// Create new stack object
var stack = /* This is done by the 'new' keyword */ 
// Run our code
stack.push = /* Something */

基本上就是这样!希望它对你有所帮助:)

函数是一个对象,是指对象的特定实例。

如果函数中有一个没有this的函数,则该函数是该函数的本地函数。

有了这个,内部函数就变成了对象的方法,可以调用它来执行一些动作。

最新更新