It is common for developers to worry about optimization while doing initial programming. Some write extremely complex code in the belief that it is optimized. Unfortunately, this code is often slower than it might otherwise be. Additionally, the compiler may be unable to optimize the code. I find optimization is rarely necessary and effective optimizations are difficult to predict.
This post present the my optimization rules. Future posts will present the techniques I use to avoid optimization, and perform optimization when needed.
Don’t Optimize
Optimization can easily distract from the most important consideration of getting it right. Even if you get it right, it likely the code will be more complex, and possibly slower. Clean simple code is much easier to understand, and more likely to be optimized by the compiler.
The libraries provided with the language are usually optimized. The libraries may be optimized for the hardware on which they run. Writing your own code rather than using the libraries will usually have a performance cost as you loose these optimizations.
Don’t Optimize Now
A majority of code, although necessary, does not run often or take much time. Any time spent optimizing this code will raise the cost and complexity of the code without providing a significant performance gain. Until the code is in use it is often difficult to determine which code will get the most use.
Profile to Identify the Problem
Before you set about optimizing your code, you need to be able to determine which code is worth optimizing. After determining the functionality which is slow, profile the time it spent in various sections of the code. Wall clock time as well as CPU time may be necessary as the problem may be data access time rather than CPU time.
If your code runs over the web, it may be worthwhile tracking request response times. The results can be aggregated to provide an ongoing performance profile. This can be used to determine which requests are slowest or take the most time overall. When it is time to optimize these are your candidates.
As you test your optimizations, redo the profile to determine if you are succeeding. It is common for changes which appear to be optimizations to actually slow code down. You need to measure as you go to validate your changes. You also need to validate that the optimized code still works correctly.
Optimize the Component that is Taking 80% of the Time
To provide a significant result from you optimization you need to start with a significant cost. If you eliminate 10 pieces of code taking 1% of the time you reduce the time by 10%. If you can cut half the time in code taking 80% of the time, you come close to reducing the time in half.
This is a good place to experience the 80/20 rule. Simply stated it is that eighty percent of the time is spent in twenty percent of the code. This is an approximation and often the split may be 90/10 or 70/30. In any case, the other code can not give significant performance gains.
Find an Optimization that is 10 Times Faster
If it is worth optimizing your code, you should be able to find an optimization that is 10 time faster. To achieve these kinds of optimizations you likely need to rethink how the code is achieving its results. If you can not find a significant optimization, you may already have a close approximation of the optimal solution. Consider the effects of optimizing the code on its maintainability and correctness. Is faster code which gives an incorrect answer better?
There are cases where micro optimizations are worthwhile. Graphics (or gaming) code tends to be be CPU intensive, and is where micro optimization is more commonly applied. These optimizations need to be commented so that some well meaning programmer does not remove them while fixing other problems.