Recursive prototypical inheritance in javascript?

advertisements
Object.create = function (o) {
    function F() {}
    F.prototype = o;
    return new F();
};

From Prototypal Inheritance in JavaScript

I've been using this code for a while to create new objects inheriting from previous ones. However I ran across a little surprise.

a = {
    foo: [1,2,3]
}

b = Object.create(a);
// b.foo -> [1,2,3]
b.foo = "test";
// b.foo -> "test"
// a.foo -> [1,2,3]

c = Object.create(a);
// c.foo -> [1,2,3]
c.foo[0] = 'test';
// c.foo -> ["test",2,3]
// a.foo -> ["test",2,3]

In trying to change c.foo I changed a.foo instead, c.foo showing the change because it's inheriting from a. The only solution I see right now is to only modify direct properties of b:

d = Object.create(a);
d.foo = Object.create(a.foo);
d.foo[0] = 'text';

I'm sure there's a better solution I'm missing! How can I create new objects from old objects without risking modifying the original?


+1 for referencing Crockford =D

I think arrays are always passed by reference, and the array is never copied. I think Array.slice would copy it, but that's a fringe case...

The create function is mostly used to copy functions and such. I don't ever use that method, as I just create a constructor function:

function a() {
    this.foo = [0, 1, 2];
}

This way, you'll always get a new array for each call. Just do b = new a(); It works for me...

I try to avoid inheritance, because there's always problems with it. I would just use the constructor, then assign new variables to it (not the prototype). Multiple inheritance gets tricky though...