Reputation: 2385
In javascript, variables referring to objects are passed a "copy of the reference". I am struggling with this concept as it relates to merging two objects, and the effect on the references to those objects. Attempting to use underscore's extend, take the following (coffeescript) code:
a = {
id: 1
type: "cat"
name: "Angry"
}
b = {
id: 1
type: "dog"
owner: "Bill"
}
c = a
d = c
e = b
_.extend(a, b)
b = a
d.home = "Nashville"
console.log(a) //Object {id: 1, type: "dog", name: "Angry", owner: "Bill", home: "Nashville"}
console.log(b) //Object {id: 1, type: "dog", name: "Angry", owner: "Bill", home: "Nashville"}
console.log(c) //Object {id: 1, type: "dog", name: "Angry", owner: "Bill", home: "Nashville"}
console.log(d) //Object {id: 1, type: "dog", name: "Angry", owner: "Bill", home: "Nashville"}
console.log(e) //Object {id: 1, type: "dog", owner: "Bill"}
As we can see, underscore did not 'merge' the objects. Instead, what has happened is that underscore set the attributes of the object referred to by b
on the object referred to by a
. Later, when we replace the reference held by b
to point at the object referred to by a
, e
continues to hold a reference to the object originally referred to by b
. This is because e
was not assigned a reference to b
, but rather a copy of the reference held by b
. Similiarly, d
holds a reference, not to c
but to the object referred to by a
.
I would like to find a way to truly merge the two objects, so that all references to both objects point at a single destination. Is this possible in Javascript, or am I precluded from doing this as a result of Javascript's object passing structure?
Upvotes: 2
Views: 232
Reputation: 665564
I would like to find a way to truly merge the two objects, so that all references to both objects point at a single destination. Is this possible in Javascript, or am I precluded from doing this as a result of Javascript's object passing structure?
That's impossible without changing the references, i.e. having access to all the variables and re-assigning them with the new reference value - in your case, e = b
just as you did b = a
.
To get the expected result, you might want to do _.extend(a, b); _.extend(b, a);
so that they have the same properties - however they stay two different objects.
Upvotes: 3