Short-Circuited Evaluation

Short circuit evaluation are supported in many popular languages nowadays, but few programmers understand it well enough to make full use of it.

In if statements involving multiple conditions, sometimes evaluating the first condition is sufficient to determine the result of the entire evaluation. For &&, all conditions must be true. Therefore if the first condition is false, the entire condition become false. For ||, no statement must be false. The program below shows that the portion is not evaluated at all.


public class ShortCircuit {

    public static boolean returnsTrue() {
        System.out.println("returnsTrue() called");
        return true;
    }

    public static boolean returnsFalse() {
        System.out.println("returnsFalse() called");
        return false;
    }

    public static void main(String[] args) {
        System.out.println("Evaluating &&");
        if (returnsFalse() && returnsTrue() {
            System.out.println("Never printed");
        }

        System.out.println("Evaluating ||");
        if (returnsTrue() || returnsFalse()) {
            System.out.println("2nd condition not evaluated.");
        }
        System.out.println("Ended.");
    }
}

The output of the program shows that for both evaluations, only the first condition is checked, even though there are two method calls on those lines.

Evaluating &&
returnsFalse() called
Evaluating ||
returnsTrue() called
Ended.

The advantage of this is quicker evaluation of conditions by putting the simpler condition in front, giving more chances of short circuits:


if (someBoolean && longCalculation()) // ...

if someBoolean is false, the long calculation is actually avoided totally, making your code run faster and not perform uncessary calculations.

Pitfalls

On the other hand, if a developer is unaware of such a “feature”, he may introduce unintentional bugs:


if (someBoolean && updateDatabase()) // ...

The method being called returns a boolean, but it happens to perform some necessary update on the database. In this case the method may be accidentally missed, due to the short-circuit of the someBoolean variable. Therefore the code should be modified to ensure execution of the updateDatabase method.


if (updateDatabase() && someBoolean) // ...

If you prefer defensive programming, refactor the database method out from the if statement:


boolean databaseResult = updateDatabase(); // must call
if (someBoolean && databaseResult) // ...

In conclusion, this concept is not just a technique to better coding, but a must-know in order to avoid issues as described above.

Additional Notes

You can avoid short-circuit evaluation by using & and | instead of && and ||. However ensure they are only used on booleans as & and | also perform bitwise operations in Java. C# has the exact same operators. VB.Net’s default And and Or do not support short-circuit evaluation, instead they use introduced operators AndOnly and OrElse for short-circuits.

RSS feed for comments on this post · TrackBack URL

Leave a Comment