Tuesday, 17 January 2012

Accessing members by name

One sometimes misunderstood feature of ActionScript is that as well as accessing members of a class directly and using accessors it's possible to do so using the name of the member, passed as a String to the class. Misunderstood as there is a right way to use this and a wrong way to use this. And the wrong way is incredibly slow, so much so it should be avoided at all times.

The right use for this feature is to turn any Object into an associative array. ActionScript doesn't have an associative array class but it doesn't need one, as any Object, provided it's class is dynamic, can have members added and then referenced by name, as if it were an associative array. There are many uses for this, although not many in a web game.

But the class only needs to be dynamic to add members at runtime. Members that are part of the class definition can be read by name. The syntax looks like this:

    iSum += v["iX"] + v["iY"];

Compared with accessing the members directly.

    iSum += v.iX + v.iY;

The problem with doing this is it's slow, incredibly so. I've updated my accessor test (embedded below) to include the above, and it is ten times slower than using accessor functions, fully fifty times slower than accessing the members directly.

And that's not the worst example I've seen. The worst looks something like this.

    level = game["level" + level_num];

preceding the lookup with a relatively expensive String addition. This could be replaced with an array lookup. If a String is used as it contains more information then replace them with constants. E.g. 

    level = game.levels[kLevelBase + level_num];

Unless a String won't be known until runtime it is always possible to replace it with constants as above.

No comments:

Post a Comment