为什么实例方法不能按预期工作?

时间:2011-10-07 02:47:27

标签: javascript oop

(function() {
     window.gArr = new ExtArray();
})();

function ExtArray() {
     this.bounce = function() {
         document.write("Bounced successfully!");
     };
}

ExtArray.prototype = new Array;
ExtArray.prototype.first = function() {
     document.write(this[0]);
}

var eArr = new ExtArray();
//all three work
eArr.bounce();
eArr.push("I am first! ");
eArr.first();
// invoking global
gArr.bounce(); // it works
gArr.push("No, it is me who is really first! "); // doesn't work
gArr.first(); // doesn't work

为什么不起作用?

2 个答案:

答案 0 :(得分:1)

> (function() {
>      window.gArr = new ExtArray(); })();

为什么这只是优先选择:

var gArr = new ExtArray();

它们功能相同(除非没有 window 对象,否则第一个会失败);

> function ExtArray() {
>      this.bounce = function() {
>          document.write("Bounced successfully!");
>      }; }

在页面加载完成后使用 document.write 将首先清除整个文档(即HTML标记之间的所有内容)并写入传递给函数的任何内容(在这种情况下,两个字符串)。

> ExtArray.prototype = new Array;
> ExtArray.prototype.first = function() {
>      document.write(this[0]); 
> }

如上所述, document.write 具有破坏性。

> var eArr = new ExtArray(); 
> //all three work 
> eArr.bounce();
> eArr.push("I am first! ");
> eArr.first();

据推测,这是在加载事件之前运行的。

> // invoking global 
> gArr.bounce(); // it works 
> gArr.push("No, it is me who is really first! "); // doesn't work 
> gArr.first(); // doesn't work

“不起作用”的位是因为您在修改 ExtArray.prototype 之前初始化了 gArr ,因此它具有实例方法 bounce 但在声明构造函数时仍然具有默认原型。

请记住,一旦声明完成,代码将按顺序运行,因此 gArr = new ExtArray() ExtArray.prototype = new Array; 之前运行,依此类推。

此外,一个实例有一个内部 prototype 属性,它在创建它的瞬间引用构造函数的原型,之后无法更改(除了Mozilla已弃用的< strong> proto 属性)。因此,更改contsructor的原型不会改变已经构建的任何实例的内部原型。

答案 1 :(得分:1)

定义window.gArr后,您应该定义ExtArray.prototype

function ExtArray() {
     this.bounce = function() {
         document.write("Bounced successfully!");
     };
}

ExtArray.prototype = new Array;
ExtArray.prototype.first = function() {
     document.write(this[0]);
}; // <-- semicolon will be REQUIRED here.

(function() {
    window.gArr = new ExtArray();
})();

DEMO: http://jsfiddle.net/Vg3Ze/