For the following code, why the propB
of myObj
is updated? And why test.childObj
doesn't have the own property propB
?
var myObj = { propA: '', propB: [] }
var fatherObj = {
childObj: null,
init: function() {
this.childObj = Object.create(myObj);
this.childObj.propA = 'A';
this.childObj.propB.push(2);
}
}
var test = Object.create(fatherObj);
test.init();
console.log(myObj.propB.length);
console.log(test.childObj.hasOwnProperty('propA'));
console.log(test.childObj.hasOwnProperty('propB'));
Just as object properties can store values of any primitive data type (as well as an array or another object), so too can arrays consist of strings, numbers, booleans, objects, or even other arrays.
JavaScript arrays are zero-indexed: the first element of an array is at index 0 , the second is at index 1 , and so on — and the last element is at the value of the array's length property minus 1 . JavaScript array-copy operations create shallow copies.
Using Object.create
you do not copy an object, but you create a new object that inherits the passed one:
this.childObj { } -> myObj { propA: "", propB: [] }
Now when you get a property, it gets looked up in the inheritance chain. As it can't be found in the child object, it gets looked up in myObj
. That is usually not a problem, as setting an objects property directly sets it on the object itself without using the inheritance chain, therefore this:
this.childObj.propA += "test";
looks up propA
on myObj
but sets propA
on the childObj
. With reference types however, you do not rewrite the property, therefore this:
this.childObj.propB.push(1);
looks up propB
in myObj
, and pushes to that, the result is:
this.childObj { propA: "test" } -> myObj { propA: "", propB: [1] }
To resolve that, the childObj has to have its own propB
array:
this.childObj.propB = this.childObj.propB.slice();
That results in:
this.childObj { propA: "test", propB: [1] } -> myObj { propA: "", propB: [1] }
and now pushing to propB
pushes to the array in childObj
.
That is because myObj
becomes a prototype of newly created test
object (caused by creating it via Object.create.
Due to you just modify underlying prop propB
of childObj
(and not assign the new value like for propA
) you only modify the prop of prototype. Please read more about inheritance in javascript.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With