【问题标题】:How to access the instance when prototyping with constructor functions?使用构造函数进行原型设计时如何访问实例?
【发布时间】:2012-06-19 11:04:03
【问题描述】:

我正在通过 prototype 方法扩展构造函数类的功能,但我无法弄清楚如何访问即将成为构造函数类的实例。

假设我们有以下类:

Bla = function()
{
    this.a = 5;
}

足够简单。现在,我将用一个非常简单的方法来扩展它......

Bla.prototype.f = function(){console.log("Abdf.")};

new Bla().f(); //Logs "Abdf as expected."

但是,如果我想访问 a 属性 (5) 怎么办?假设我正在尝试像这样扩展构造函数类:

Bla.prototype.f2 = function(b){return b * here_are_the_problems.a};

显然使用this 指的是别的东西。我应该改用什么?

【问题讨论】:

标签: javascript oop constructor prototype


【解决方案1】:

使用this 关键字访问任何实例属性或方法。 this 代表实例。由于a 是实例属性,prototype 方法是实例方法,因此可以在prototype 中访问。

Bla = function() {
    this.a = 5;
};
Bla.prototype.foo = function () {
   console.log( this.a );
}

var x = new Bla;
x.foo(); // logs 5
​

但是,如果我们直接给 Bla 添加一个方法...

Bla.bar = function () {
   console.log( this.a ); // ERRORRRRR
}

因为 bar 不是实例 (prototype) 方法。在这种情况下,它是Blastatic method 并且没有实例,this 指的是函数Bla.bar,在这种情况下没有属性a

【讨论】:

  • 您应该将a 称为对象的属性,而不是变量。 Bla 构造函数中的任何实际变量都不能从原型方法直接访问。
  • @Trevor,什么是“static method”?
  • 静态方法是不需要实例且无权访问实例变量的类的方法。您通常会编写其中之一来创建类的实例或与类类型相关的方法。
【解决方案2】:

使用this 来引用调用方法的对象...

console.log(this.a);

有几种方法可以设置this 的值。一是如果函数作为对象的方法调用,一般指调用函数的对象。

Bla = function()
{
    this.a = 5;
}


Bla.prototype.f = function(){console.log(this.a)};

var bla = new Bla();

bla.f(); //Logs 5

所以你可以看到,由于f 被调用为Bla 的实例的方法被bla 变量引用,f 中的this 的值将被设置为引用相同的对象。

【讨论】:

  • 特别说明:如果您使用对象方法作为事件处理程序(在其他情况下,但事件处理是最常见的情况),通常会在元素的上下文中调用该方法。 IE。在element.onclick = bla_instance.some_method; 中,this 关键字实际上将引用元素而不是 bla_instance(如果使用 jQuery 绑定事件也是如此)。
  • @Flambino:是的,虽然我不会说它使用元素的“范围”。范围与this 是一个非常独立的问题,它指的是调用上下文。但是,是的,调用上下文没有绑定到原始对象(除非您使用Function.prototype.bind() 创建一个)
  • 你说得对,我的意思是写“上下文” - 修正了我的评论。是的,.bind(或$.proxy,如果您在不支持本机绑定的旧浏览器中使用jQuery)是解决方法。我想也应该提到这一点:-P
  • @Flambino:this 的语义有很多方面。一个人可以说得太少,留下漏洞,或者说太多,偏离原点。 :)
  • 是的,解释this 可以很快偏离正轨。但我认为事件处理是上下文混淆的常见来源,所以我想我最好提一下。特别是如果最初的问题是因为this.a 似乎无法正常工作:)
猜你喜欢
  • 2013-04-14
  • 1970-01-01
  • 2020-07-11
  • 1970-01-01
  • 1970-01-01
  • 2013-04-23
  • 1970-01-01
  • 2012-08-21
  • 1970-01-01
相关资源
最近更新 更多