Be wary of micro-benchmarks baring speed improvements
I've seen some links recently to the Round up of ActionScript 3.0 and Flex optimization techniques and practices and I'm afraid. I'm afraid that entries on that list are going to become gospel and code that doesn't use the tricks listed will be labeled bad. Knuth said it best, "We should forget about small efficiencies say about 97% of the time: premature optimization is the root of all evil." While the author frames the discussion correctly stating "You have to learn when to use some techniques and when to leave some out." I don't think he does enough to call out the type of optimization each entry is, or more importantly, how these techniques were derived.
One of the key tenants of any performance reporting is carefully detailing the environment and method used to construct the test. I'll focus first on the environment. With any ActionScript 3.0 and in particular Flex optimization techniques there are factors beyond the code that impact the effectiveness of a possible performance tweak. Depending on your target audience (e.g. intranet, internet, etc.) some of these techniques may work against you (i.e. your tweak makes your code run slower in certain cases).
The first is the Flex compiler. The same code compiled with different versions of the compiler will produce different performing SWFs. The Flex SDK is continually improving the optimizations applied to the generated SWF. That means that in some cases a performance tweak you made for the Flex 3.0 SDK may end up fighting the compiler and producing slower code with 3.2. As such keep track of any performance tweaks you make and be sure to test them whenever you change the tools you use to produce your SWFs. #19 is a classic example of a code pattern that in many cases the compiler could optimize automatically.
If we assume that the compilation tools are consistent the next big factor that will affect your performance is the Flash player itself. Remember one of the big advances that Adobe did with Flash 9 was introduce a virtual machine into the player that has just it time (JIT) compilation support. Each version of the Player makes tweaks to the JIT that can impact how your code runs. That might mean code which ran one way in a previous version of the player now behaves differently possibly even running slower. #13 and #15 on the list are examples of how the player may impact performance.
Of course the other half of runtime in the machine that the Flash player is running on. While Adobe does a fantastic job of providing a consistent cross platform runtime, they don't have any hard guarantees about the performance across platforms or hardware. Maybe memory management on one machine makes your code page fault more frequently which will slow it down. Maybe hyper threading or hardware acceleration of Pixel Bender filters helps the code run faster. The wide variability in hardware and software that the Flash player can run on means that there are many performance optimizations that could easily backfire in certain situations if you are really trying to eek out every millisecond of performance.
The other area I'd like to touch on beyond the environment is the testing methodology. The article gives almost no information about how each of the performance techniques was measured. While references are listed at the bottom the hints and tips are not cited well enough to easily track down the source. To take #1 "Array instantiation" as an example: Did someone write a single function that created X arrays using each technique and measure the total time taken? Were they two methods in the same SWF or were they different SWFs? Did they vary the order that the methods were called? How many times did they run the loop? Did they examine what happened when garbage collection started happening? Did they create these Arrays within the scope of a method, a class, as a static? What compiler did they use? What Flash Player was it tested on? What were the specifications of the machine that the tests were run on? That's just a sampling of questions that come to mind when I see a sample optimization technique. The answer to anyone of them could impact how helpful it might be to your code or even if it does anything in real code versus some micro-benchmark.
With all of that said my intent is not to dissuade you from thinking about performance optimizations but instead focus the discussion not at the micro-benchmark level but at the algorithmic level. What I mean is that for a given problem, I don't care how you initialize your Arrays, the fact that you are using bubble sort instead of heap sort means that for any reasonable implementation and application usage it will always be slower. That is the 97% that Knuth is referring to. Real world performance problems are almost always going to be inefficient algorithms long before your Array initialization technique starts taking up the majority of your time.
Scanning the list of techniques, I consider these to be more algorithmic focused and worth thinking about first:
- 26: given that the Flex documentation continues to say this I'm inclined to agree with this one
- 27: more objects to layout, more objects to keep in memory, etc. make this a good thing to keep in mind
- 37: it's much better to not even need to think about needing to draw something, I'd add that includeInLayout is another important setting
A couple other observations:
- 2: I'd say any object that you don't need is expensive so don't create what you don't need
- 12: ideally you're using polymorphism so you don't even need to do branching but if not the axiom of Keeping the Common Case Fast applies here keeping in mind there is still a chance that the compiler or JIT can impact performance
I'm know my observations about items from the original list could be debated. I still think it is a great list of things to try, but in general don't treat it as gospel. Overall I want to emphasize that minor tweaks will not impact performance as much as algorithmic inefficiencies. Keep that in mind next time you need to speed up some code.