Order of execution for an if with multiple conditionals
Asked Answered
B

3

78

In an if statement with multiple conditionals, is the second conditional executed if the outcome of the first is clear?

example:

if(i>0 && array[i]==0){
}

If I swap the conditionals a segfault may occur for negative values of i, but this way no segfault occurs. Can I be sure that this always works or do have have to use nested if statements?

Bagnio answered 16/3, 2010 at 16:19 Comment(1)
See #629026Fighterbomber
A
108

This type of evaluation is called short-circuiting. Once the result is 100% clear, it does not continue evaluating.

This is actually a common programming technique. For example, in C++ you will often see something like:

if (pX!=null && pX->predicate()) { bla bla bla }

If you changed the order of the conditions, you could be invoking a method on a null pointer and crashing. A similar example in C would use the field of a struct when you have a pointer to that struct.

You could do something similar with or:

if(px==null || pX->isEmpty()} { bla bla bla }

This is also one of the reasons that it is generally a good idea to avoid side effects in an if condition.

For example suppose you have:

if(x==4 && (++y>7) && z==9)

If x is 4, then y will be incremented regardless of the value of z or y, but if x is not 4, it will not be incremented at all.

Artilleryman answered 16/3, 2010 at 16:20 Comment(1)
+1. Worth mentioning, an exception to side effects in an if condition is checking for error return values: if (function_that_returns_neg_on_error(param1, param2) < 0) { perror("function"); return -1;}Tricorn
S
47

The operators && and || guarantee that the left-hand side expression will be fully evaluated (and all side effects applied) before the right-hand side is evaluated. In other words, the operators introduce a sequence point.

Additionally, if the value of the expression can be determined from the lhs, the rhs is not evaluated. In other words, if you have an expression like x && y, and x evaluates to 0 (false), then the value of the expression is false regardless of y, so y is not evaluated.

This means that expressions like x++ && x++ are well-defined, since && introduces a sequence point.

Sofiasofie answered 16/3, 2010 at 16:57 Comment(0)
J
22

From draft 3485 (n3485.pdf) Its clearly stated that

5.14 Logical AND operator [expr.log.and]

logical-and-expression: 
      inclusive-or-expression
      logical-and-expression && inclusive-or-expression 
  1. The && operator groups left-to-right. The operands are both contextually converted to bool (Clause 4). The result is true if both operands are true and false otherwise. Unlike &, && guarantees left-to-right evaluation: the second operand is not evaluated if the first operand is false.
  2. The result is a bool. If the second expression is evaluated, every value computation and side effect associated with the first expression is sequenced before every value computation and side effect associated with the second expression.
Jaleesa answered 22/1, 2014 at 12:23 Comment(2)
what do you mean by unlike &? If i use & then the order is not guaranteed?Parboil
Ex: if((func1() & func2()) == true) vs if(func1() && func2())Parboil

© 2022 - 2024 — McMap. All rights reserved.