Sorry, If-Else Statements Aren’t Bad at All
A clarification on the controversial “Stop Using X” advice doing the rounds
Recently, I came across a programming piece that put forth a rather controversial stance against the use of a basic if-else
control flow.
I’m specifically going to respond to the article “Stop Using If-Else Statements,” which offered some misleading programming advice right from its (clickbait) title.
Subsequently, I’ll walk you through a few common mistakes that developers make when using if-else
statements and how to fix them.
What Was Wrong About That Article?
- The piece made sweeping claims by calling
if-else
statements evil. It went on to show awfully wrong use cases of the most basic programming control flow. - The complex
if-else
clauses the author wrote not only did way too much work but were also laughably wrong. Addingthrow
statements in everyif
condition and putting an unnecessaryelse
block at the end made no sense. - To add to the misery, the bloated solution suggested creating a class for every single state condition (with confusing naming conventions), thereby adding unnecessary abstraction.
- Introducing more than 200 lines of code for a mere ten lines of conditional logic defies the basic coding principle: Keep it simple and stupid.
- Ultimately, the final solution of the article contradicted its own title. It simply delayed the use of
if-else
conditions by not placing it at the top level of the code. Despite being a good practice, this was not even mentioned in the whole story.
The sad part is such misleading titles can build misconceptions in the heads of junior programmers. Yes, a rare few readers who praised the article were the ones who’d just started out programming or were about to.
In summary, the article was like a code with obvious bugs. Instead of fixing the root cause of the problem, it put the blame on the whole if-else
paradigm, showed a replacement that wasn’t like-for-like, and recommended using that for all programming solutions.
How to Use if-else Statements Elegantly?
I’d like to declare that if-else
statements aren’t bad. It’s the way that you use (or misuse) them that could lead to messy code.
There are no one-size-fits-all solutions in programming. Similarly, there aren’t any bad practices when using if-else
or else-if
conditions.
Of course, using else
statements should be done carefully, as it's difficult to predict the scope of it. If any condition besides the if
clause goes into else
, that might not be what you actually want.
If you force yourself to look for workarounds for the basic if-else
flow, you’ll only get bogged down with unnecessary boilerplate code and abstraction.
Yet, there are some instances where I’ve seen and used if-else
statements in the wrong fashion across different languages.
Avoid if-else When Assigning Value to a Variable
Once upon a time, I did write something like this in Java (though I’m using Swift in the examples below for the sake of brevity):
var num : Int!if someCondition{
num = 10
}
else{
num = 20
}
While it might not seem bad, you could easily end up inverting or tweaking the conditional logic to give a whole new meaning. The branching logic also brings a little code duplication, as we’re assigning the variable num
in multiple blocks, which is not necessary.
Thankfully, we can use the ternary operator, which is like an if-else
statement in a single line:
num = isCondition ? 10 : 20
Alternatively, for some use cases, you could also set default values at variable declaration time to remove the use of else
.
As a dynamically typed language, Python requires you to assign values during declaration. So, using the scenarios above is rather obvious there:
#Python
num = 10 if isCondition else 20
Add Early Exit Conditions to Avoid else Part
Often, the use of else
in blocks with multiple ifs
and else-ifs
is to handle default scenarios and deal with errors.
We all must have written blocks like the following:
if someBoolean {
// ...
} else {
throw Exception("xxxx")
}
The else
part is like a fail condition that we can easily put at the start of the control flow:
if !someBoolean{
throw MyException()
}
No wonder Swift provides us with a guard let
statement to add an early fail condition in case anything is wrong. This is really handy with nested if
conditionals.
Extract Long Conditionals Into Functions
When you’re dealing with if-else
blocks, conditional statements that involve binary operators are needed at times. &&
and ||
operators are useful for addressing specific conditions and reducing the amount of nested if
blocks.
But it can easily get out of hand and turn into a long, unreadable if
condition.
Here’s a look at what happens:
if a > 0 && isEnabled && b > 10
{...}
else
{...}
You can shorten the code above to your liking:
- For one, if you’re using multiple booleans that aren’t mutually exclusive, replace them with enums.
- You can extract the condition into a separate function, thereby making things more comprehensible.
func customCondition() -> Bool{
return a > 0 && isEnabled && b > 10
}
Now, simply pass on the function above in the if
condition:
if customCondition()
{...}
else
{...}
Conclusion
Remember, if-else
statements aren’t bad and you cannot ever eliminate them from your codebase.
But you can make your life easier by ensuring that there’s no code duplication and keeping the if-else
blocks interrelated (not mutually independent conditions).
That’s it for this one. Thanks for reading.