我在我的项目中遇到了一个问题,它与JS的原型继承有关。并将主要问题抽象如下:
var parentObj = {
value:"parent value",
obj: {
obj: "parent obj value"
}
}
var childObj = Object.create(parentObj)
以文字对象的方式创建parentObj
,并根据它创建childObj
并将其作为原型。
在第一种情况下如下:
childObj.value ="child value"
childObj.obj = {obj:"child obj value"};
console.log(parentObj)
console.log(childObj)
输出是:
{ value: 'parent value', obj: { obj: 'parent obj value' } }
{ value: 'child value', obj: { obj: 'child obj value' } }
此结果符合预期。
但对于第二种情况如下:
childObj.value ="child value"
childObj.obj.obj = "child obj value";
console.log(parentObj);
console.log(childObj);
输出结果为:
{ value: 'parent value', obj: { obj: 'child obj value' } }
{ value: 'child value' }
parentObj
已更改。这个结果对我来说有点混乱,有什么帮助吗?
答案 0 :(得分:0)
当您使用x = Object.create(y)
时,您会获得一个x
作为其y
属性的对象__proto__
。
__proto__
允许在JS中进行属性委派。
属性委派意味着当您向对象询问属性时,如果该对象没有该属性,该对象将询问其父对象(__proto__
)。如果父对象也没有它,那么它将询问它的父对象。
如果在链用尽之前找到该值,则返回该值,否则返回undefined
。
在你的情况下
var parentObj = {
value:"parent value",
obj: {
obj: "parent obj value"
}
}
var childObj = Object.create(parentObj)
parentObj
是__proto__
childObj
console.log(childObj.__proto__ === parentObj) // true
此外,childObj
不拥有自己的名为.obj
或.value
的属性。
您可以使用Object.getOwnPropertyNames
进行检查。
这是确定对象上是否存在属性的唯一方法。
console.log(Object.getOwnPropertyNames(parentObj)) // ["value", "obj"]
console.log(Object.getOwnPropertyNames(childObj)) // []
执行childObj.obj.obj = ...
后,您可以修改对象.obj
上的属性parentObj.obj
。
相反,当您执行childObj.obj = ...
时,您会在.obj
上添加新属性childObj
。
childObj.obj = "child obj value"
console.log(Object.getOwnPropertyNames(childObj)) // ["obj"]
PS:如果您想了解有关hte主题的更多信息,我建议http://www.javascripttutorial.net/javascript-prototype/