-3
    #include <stdio.h>
    int main()
    {
       int x, y, z; 
       x=y=z=1; 
       z = ++x || ++y && ++z; 
       printf("%d, %d, %d", x, y,z);
       return 0;
    }

I am getting output 2, 1, 1. I need and explanation why Y is 1 in output?

Peter - Reinstate Monica
  • 15,048
  • 4
  • 37
  • 62

3 Answers3

3

The || operator is short-circuiting; the right operand is not evaluated (and side effects never executed, i.e. the variables never incremented) if the left operand evaluates to != 0.

(Remember that "multiplication comes before addition", or in boolean logic AND comes before OR. Because of the operator precedences the expression becomes, fully bracketed, (++x) || ((++y) && (++z)); in other words, everything to the right of || is the OR's ignored right hand side.)

The evaluation of the left operand ++x increments x to 2. z is assigned the boolean value of the result of || which is 1, as it was all along.


As an aside, gcc warned and I think it is true that the statement is also undefined behavior. The C 11 standard draft n1570 says in 6.5/2:

If a side effect on a scalar object is unsequenced relative to [...] a value computation using the value of the same scalar object, the behavior is undefined.

The standard gives the example of i = ++i + 1; for this. In your right hand side expression z plays that role. The side effect is the increment, the value computation is the && sub-expression.


1 It is possible (i.e. I'm not sure) that it is defined as long as the right hand side is never evaluated. In that case the compiler would be allowed to assume that ++x is never 0 and omit the test. The generated code for the complicated boolean expression would just boil down to an increment of x.
Peter - Reinstate Monica
  • 15,048
  • 4
  • 37
  • 62
2

The part || ++y && ++z is not evaluated, because ++x is already true. See

Short circuit evaluation

cwschmidt
  • 1,194
  • 11
  • 17
1

The logical operation || is so-called "short-circuit" or "lazy" operation. If the left operand of such an operator is evaluating to logical true or a non-zero, the right operand won't be evaluated.

So in your case:

z = ++x || ++y && ++z; 

++x is evaluating to 2, making x equal 2. This is non-zero, so everything on the right side is not evaluated, so y and z are not incremented. And z is assigned by the result of the logical OR operation, i.e. 1. And this is what you see.

Eugene Sh.
  • 17,802
  • 8
  • 40
  • 61