Get Your Conditions in Order
It’s programming 101 but it’s easy to miss in practice. If a condition has multiple expressions, some may never be evaluated. Use that fact to your advantage.
Be Frugal
I like to shop at Amazon but will never believe there are people who actually sort their results from most expensive to least expensive. Why?
If you’re anything like me, you sort from least expensive to most expensive and you scroll down the list until you find what you’re looking for.
The same principle applies to your Ruby conditions. Be frugal. Take the following model:
class Profile < ActiveRecord::Base
belongs_to :user
def active?
!user.suspended? && !archived?
end
end
Code like this can slip through the cracks fairly easily because… it works. The tests are green, the code is clean![1]
The problem is that we’re not being frugal. Checking whether the user is suspended requires hitting the database, making the first expression more expensive than the second. We’re out of order.
There are four possible combinations of whether a profile is archived and whether its user is suspended. How our code is currently written, here’s how Profile\#active?
would play out:
suspended? |
archived? |
active? |
# of Queries |
true |
true |
false |
1 |
true |
false |
false |
1 |
false |
true |
false |
1 |
false |
false |
true |
1 |
Simply changing the order of the conditional expressions produces the same results, only with fewer queries:
def active?
!archived? && !user.suspended?
end
suspended? |
archived? |
active? |
# of Queries |
true |
true |
false |
0 |
true |
false |
false |
1 |
false |
true |
false |
0 |
false |
false |
true |
1 |
In our example, the expression performing fewer queries is clearly less expensive to evaluate. In your own code, any number of factors will come into play, but it’s worth the effort to get your conditions in order.
Comments
You can even have undefined methods in the condition:
false && this_method_is_not_defined
=> false
To be honest. I actually sorted from most expencive to least expensive a few months ago when I was searching for a new I7 CPU and got a lot of “cluter”. I just wanted the expensive I7.
Long story short. People use it. :)