在下面的示例中,我注意到注释"修复了委托的构造函数引用",我很好奇 - 我可以在添加javascript行后显示"不工作/然后工作吗?"
完全要点=> https://gist.github.com/getify/5572383
先感谢您
function Foo(who) {
this.me = who;
}
Foo.prototype.identify = function() {
return "I am " + this.me;
};
function Bar(who) {
Foo.call(this,"Bar:" + who);
}
Bar.prototype = Object.create(Foo.prototype);
Bar.prototype.constructor = Bar; // "fixes" the delegated `constructor` reference
Run Code Online (Sandbox Code Playgroud)
javascript中的函数实际上是对象.当我们Foo在Javascript中创建任何函数时,解释器会自动创建一个prototype属性Foo.prototype,该属性本身就是一个对象.然后,解释器constructor在此对象上创建一个属性,该属性引用Foo自身:
console.log(Foo.prototype.constructor); // reference to Foo;
console.log(Foo.prototype.hasOwnProperty("constructor")); // TRUE;
Run Code Online (Sandbox Code Playgroud)
当我们创建Bar函数时,会发生同样的过程.但后来我们引入了一个区别.不同之处在于我们Bar.prototype使用以下代码手动覆盖对象:
Bar.prototype = Object.create(Foo.prototype);
Run Code Online (Sandbox Code Playgroud)
现在Bar.prototype有一个我们手动创建的新对象.这个新对象没有constructor属性,因为它是由我们而不是解释器创建的:
console.log(Bar.prototype.hasOwnProperty("constructor")); // FALSE
Run Code Online (Sandbox Code Playgroud)
所以Bar.prototype没有自己的constructor财产,但Foo.prototype确实如此.接下来,假设我们创建了一个实例Bar:
var myBar = new Bar();
Run Code Online (Sandbox Code Playgroud)
myBar.constructor是myBar对象上不存在的继承属性.如果我们尝试访问它,javascript解释器会在原型链中搜索constructor属性.它没有找到一个,Bar.prototype因为我们覆盖了那个对象.解释器继续搜索并最终找到该属性Foo.prototype.因此,任何引用都myBar.constructor将引用Foo.prototype.constructor,其中包含对Foo以下内容的引用:
console.log(myBar.constructor); // reference to Foo
Run Code Online (Sandbox Code Playgroud)
所以这就是我们Bar.prototype.constructor手动显式设置的原因,这样当遍历原型链时,如果我们没有覆盖它,解释器就会找到一个constructor属性Bar.prototype:
Bar.prototype.constructor = Bar;
Run Code Online (Sandbox Code Playgroud)
最终结果是对我们的对象更有用的行为:
var myBar2 = new Bar();
console.log(myBar2.constructor); // reference to Bar
Run Code Online (Sandbox Code Playgroud)
这个问题不应该经常出现,因为人们需要检查constructor对象的属性有点罕见.