4 creative ways to clone objects

There are a lot of ways to clone objects in Javascript, and some of them get pretty creative. jQuery has an excellent method for cloning objects, as does Mootools. There’s a Javascript hack we can sort of “exploit”, or we could just clone our object in plain Javascript. Let’s start with the vanilla Javascript first and move on from there.

1) A vanilla Javascript method for cloning objects

This is a somewhat simple function that will clone an object and return the clone. If a non-object value is passed in, that value is returned.

// recursive function to clone an object. If a non object parameter
// is passed in, that parameter is returned and no recursion occurs.

function cloneObject(obj) {
if (obj === null || typeof obj !== 'object') {
return obj;
}

var temp = obj.constructor(); // give temp the original obj's constructor
for (var key in obj) {
temp[key] = cloneObject(obj[key]);
}

return temp;
}

var bob = {
name: "Bob",
age: 32
};

var bill = (cloneObject(bob));
bill.name = "Bill";

console.log(bob);
console.log(bill);

If you try the above function, you’ll see that once bob has been cloned as bill, modifying values on bill won’t change the original values on bob.

2) A clever exploit of the JSON library to deep-clone objects

We can exploit the JSON library for a rather fast way of deep-cloning objects. Check it out:

var bob = {
name: "Bob",
age: 32
};

var bill = (JSON.parse(JSON.stringify(bob)));
bill.name = "Bill";

console.log(bob);
console.log(bill);

This method is nice and fast (faster as a rule than the jQuery method and possibly the Mootools function as well), and certainly rather less code than the first example. Plus, it’s pretty clever–just make sure you add a comment explaining what you’re doing. Otherwise, it could cause quite a bit of confusion!

3) Using jQuery’s $.extend() function

jQuery has a method that can be used to deep-clone objects, the $.extend() function. Let’s take a look at how it can be used:

var bob = {
name: "Bob",
age: 32
};

var bill = $.extend(true, {}, bob);
bill.name = "Bill";

console.log(bob);
console.log(bill);

Pretty handy, eh? This method is a little slower than the JSON exploit, but that shouldn’t really be a problem when you’re only doing a few clones. If you’re doing hundreds or thousands of clones, it might be time to think about the JSON exploit or another solution.

4) Using Mootools’ clone() function to clone objects

Last but not least, the Javascript library Mootools also provides a means of cloning objects–the rather aptly named clone() function. Observe the wild clone() in its natural habitat:

var bob = {
name: "Bob",
age: 32
};

var bill = Object.clone(bob);
bill.name = "Bill";

console.log(bob);
console.log(bill);

9 thoughts on “4 creative ways to clone objects”

  1. Great article – just a few notes about your vanilla function:I think you mean `new obj.constructor`, because you’re not creating an instance otherwise (just happens to work with your `Object` example, though).

    Also an `undefined` value doesn’t work – I recommend `!obj` instead of the `null` check, since all falsy values are not objects anyway.

    (Note that recursive objects like `obj.foo = obj` also won’t work but that’s not interesting, usually.)

  2. @Anonymous: Good points–you’re correct on both counts. Thanks for the catches!@Andreas: No, I can’t say I’ve ever tried to clone a Date instance with $.extend(). To be honest, I can’t imagine why I would need to! However, I will make a note of that, thanks for pointing this out. :-)

  3. Thanks for your clear and comprehensive analysis – particularly for drawing attention to the clever (and very effective) exploit of JSON.

Leave a Reply

Your email address will not be published. Required fields are marked *

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>