Color by numbers: dojo.delegate
by Neil Roberts

I wrote a fairly advanced article over at the SitePen blog on metaclass programming. But you shouldn’t have to read through a long, technical article to find out about just one of the little gems mentioned in it. Sounds like the perfect time for a Dojo Campus cookie.

I’m about to post a fun little analogy that I wrote for the article, but it needs a little bit of explaining first. A little problem that I run in to when writing JavaScript is that I’ll have an object that I want to pass to some other function or piece of code, but I’m worried that it might get manipulated somehow by this other code and be ruined. A possible solution to this would be to create a new object and copy all the fields in, like this:

var newObject = {};
for(var key in oldObject){
 newObject[key] = oldObject[key];
}

Or you might use Dojo’s shortcut function to do the same thing:

var newObject = dojo.mixin({}, oldObject);

What you might not know is that doing the kind of for loop shown above, which is the same one that dojo.mixin does, is very time consuming. The more properties in your object, the more time consuming it is. You probably know what I’m going to say: there’s a better way to do this.

There is, it’s called dojo.delegate, you use it like this:

var newObject = dojo.delegate(oldObject);

What does delegate do? I think it’s best explained through that analogy I mentioned (taken from my SitePen article):

Let’s say that you’ve just bought a color-by-numbers book, you bring it home, and you get in trouble with your nephew who also wants to use it. But you don’t feel like driving back to the store and if you color it in, you’ve just ruined it for your nephew. But you have an idea. You take out a sheet of transparency paper, tape it over the page, and start filling it in.

In the same way, think of our original object as a color-by-numbers page that’s been partially filled in. And think of dojo.declare as putting transparency paper over our original object. Now when we write variables to this new object, or “color it in”, those changes don’t make it through to the original object. Writing a variable to the new object that doesn’t exist in the original is like coloring on the transparency sheet over a blank area. Writing a variable to the new object that exists in the original is like coloring on the transparency sheet over an area that’s already been filled in. Neither action changes what’s on the page beneath, but coloring over something means we won’t be able to see what was there originally any more.

Maybe you already figured out why this is so much faster than using a for loop or dojo.mixin to copy the properties. Since dojo.delegate is just adding a protective layer to your original object, it doesn’t have to copy anything at all! This means no for loop, no copying properties, just this one simple addition. Even if you’re copying an empty object, dojo.delegate is still faster than a for loop. But on top of that, it never gets any slower, no matter how big your original object is, while the for loop approach slows down.

Also, you can keep using dojo.delegate to protect your properties:

var newObject = dojo.delegate(oldObject);
newObject.foo = "foo";
var newestObject = dojo.delegate(newObject);
newestObject.foo = "bar";

I hope you think to use this technique next time you want to protect an object from getting changed. It’s useful, and it’s fast!

Tags: , , ,

This entry was posted on Thursday, March 20th, 2008 at 8:00 am and is filed under Dojo Cookies. You can follow any responses to this entry through the RSS 2.0 feed. You can leave a response, or trackback from your own site.

4 Responses to “Color by numbers: dojo.delegate”

  1. g9yuayon Says:

    Hi Neil, dojo.delegate looks similar to dojo.clone. Would you mind explaining their differences? Thanks!

  2. pottedmeat Says:

    dojo.clone works for an object in the same way that my first two examples work: it expensively recreates the object using a for loop. dojo.declare protects an object from changes without recreating the object.

  3. g9yuayon Says:

    Thanks, pottedmeat! It’s really valuable to know the “why” of such different implementations. Would you please elaborate a bit on how dojo.declare protects an object from changes without recreating the object? Checking the dojo source, I couldn’t find where dojo.declare checks if an object is recreated, or how dojo.declare protects a delegated object.

  4. pottedmeat Says:

    It uses JavaScript’s version of inheritance

Leave a Reply

You must be logged in to post a comment.