我一直在尝试使用JavaScript享誉世界的原型继承实现。到目前为止,除了一件事之外,一切对我来说都是有意义的...

function base() {
    this.a = "baseObj property";
}
base.thisIs = "base constructor";

function derived() {
    this.b = "derivedObj property";
}
derived.thisIs = "derived constructor";

var baseObj = new base();


到目前为止,一切都很好。 baseObj.a返回“ baseObj属性”,而baseObj.constructor.thisIs返回“基本构造函数”。

但是,当我实际上使某些东西继承基础对象的值时,事情开始使我感到困惑。

derived.prototype = baseObj;
derivedObj = new derived();


最终发生的事情是derivedObj.a返回“ baseObj属性”。好。 derivedObj.b返回“ derivedObj属性”。再次好。但是derivedObj.constructor.thisIs返回“基本构造函数” ...

为此,解释器必须在derivedObj.constructor中找不到derivedObj。所以它的作用是在derivedObj.__proto__后面搜索。因为new关键字将derivedObj.__proto__设置为等于derived.prototype,我们之前将其设置为等于baseObj,所以derivedObj.__proto__最终返回baseObj

这可以解释为什么derivedObj.constructor被遗忘了。看来没用。口译员无需使用它即可获取derived.prototype;他们可以只使用derivedObj.__proto__。但是现实情况是,使用derivedObj.constructor来获取derived.thisIs的值可能很有用。

但是即使如此。它没有解释为什么在baseObj中没有忘记它。为什么.constructor中存在baseObj而不是derivedObj?它们以完全相同的方式初始化。用new关键字。

最佳答案

默认情况下,函数具有prototype属性,该属性是将函数用作构造函数时实例从其继承的对象。该prototype对象具有constructor属性,该属性指向该函数。

derived.prototype = baseObj的问题是替换了整个prototype,因此丢失了原始的derived.prototype.constructor,后者返回了derived

一种解决方法是重新分配该属性:

derived.prototype = baseObj;
derived.prototype.constructor = derived;


但是,这将更改baseObj对象。这通常是不希望的,因此正确的方法是

derived.prototype = Object.create(baseObj);
derived.prototype.constructor = derived;

关于javascript - 新的x()。constructor实际不存在吗?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/31887414/

10-09 22:25