2013-05-29 26 views
1

不能调用此代码是一个构造函数体在JavaScript的一部分:结合的这个时构造在javascript

window.addEventListener("load", function(){ 
    this._updateFilter(); 
}.bind(this)); 

_updateFilter方法属于原型构造的对象:

Constructor.prototype._updateFilter = function(){ 
    // some code 
}; 

我很困惑_updateFilter之前调用构造函数的新实例是creat编辑。因此,有没有:

var obj = new Constructor(); 

_updateFilter被调用的onload?有人可以解释这个吗?

感谢

+1

您提供的代码确实在实例创建之前确实不会调用'_updateFilter'。请向我们展示整个代码或提供一个演示这种奇怪行为的示例。 – Bergi

+0

你应该把这个片段缩小到'window.addEventListener(“load”,this._updateFilter.bind(this))' – Bergi

+0

你说得对,对不起。此方法在创建实例后调用。这个片段是来自todomvc项目的vanillsjs示例的一部分.https://github.com/tastejs/todomvc/blob/gh-pages/vanilla-examples/vanillajs/js/controller.js – carousel

回答

1

很简单,因为听者回调,甚至构造本身的定义并不意味着这是在它被定义的时候调用。实际上,构造函数只是一个函数。像任何函数声明一样,它定义了调用时会发生什么。如果我们不调用它,什么都不会发生。在构造函数的情况下,我们在创建它的一个新实例时调用它。最终,你的应用程序将调用构造函数,这里就是在那个时候会发生什么:

  1. 使用特殊new关键字,我们告诉JavaScript解释器调用构造函数并为其提供内部的新对象它。

  2. 解释器在构造函数中设置this作为该新对象在内存中的引用。

  3. 接下来,在window上创建事件侦听器。我们将回调函数传递给该侦听器,该侦听器通过this对象关闭,从而使我们当前的this引用可用。但该回调尚未执行,直到窗口的load事件触发。

  4. 想象一下,它立即发生了火灾(即实际上不是回调),我们会遇到问题。尽管this当时存在,实际上已经从Constructor.prototype继承,但它没有这样的方法_updateFilter。然后解释者检查原型链,并看到Constructor.prototype上也没有这样的功能。它会继续上链,找不到函数,并且会抛出错误。但请记住,回调不会触发。

  5. 回到实际发生的事情:接下来我们用新方法_updateFilter扩展Constructor的原型。

  6. 因此,最终窗口的load事件确实触发并且真正调用了回调。口译人员检查上是否存在_updateFilter,发现它没有,然后检查其原型链。现在它发现该函数确实存在于Constructor.prototype,并运行该代码。