I'm currently learning C, and my teacher gave us some homework. We had to identify the output of some code. I don't understand how y=4
.
The code is as follows
int main() {
int w = 3, y = 3;
printf("w = %i\n", --w + w--);
printf("y = %i\n\n", y = w + y++);
return 0;
}
Let me preface this with an important public service announcement:
When your compiler gives you a warning, any warning, you would do well to pay attention to it. The code example in your question gives rise to Undefined Behavior - in other words, the C standard does not guarantee that every compiler will give the same results, given your code. That is Always a Bad Thing.
With that out of the way, here is an explanation of what is going on.
I modified your code slightly to look at the intermediate value of w:
#include <stdio.h>
int main(void) {
int w = 3, y = 3;
printf("w = %i\n", --w + w--);
printf("w is actually %d\n", w);
printf("y = %i\n\n", y = w + y++);
return 0;
}
My compiler complains about this code with the following warnings:
order.c:6:24: warning: multiple unsequenced modifications to 'w' [-Wunsequenced]
printf("w = %i\n", --w + w--);
^ ~~
order.c:8:35: warning: multiple unsequenced modifications to 'y' [-Wunsequenced]
printf("y = %i\n\n", y = w + y++);
~ ^
2 warnings generated.
And the output is
w = 4
w is actually 1
y = 4
What is happening? Since compilers parse the statement left-to-right, the statement
--w + w--
seems to result in the following steps (for my compiler):
--w : decrement w, it is now 2
w-- : use the value of '2', but decrement w when you are done
The result is that the sum is 2+2
and the first line prints 4
, but after the sum is evaluated w
is decremented to 1
. However you cannot rely on this behavior - which is why the compiler threw a warning. As Eric Postpischil pointed out there may be situations where the order of execution might be different. "Don't do it" is the bottom line - you are courting Undefined Behavior.
Note that the fact that your program printed w equals 4
doesn't mean that this was true at any time. As you can see, when you actually print out w
it is 1.
Assuming the compiler executed these statements in the above order, we go to the next line:
y = w + y++
We start with w = 1
and y = 3
. The sum of these two is 4
, and that is the value of the expression
y = w + y++
which is therefore what is printed (4).
As a side effect, y is incremented. As it happens, either way the value of y is 4 at the end. If you change the code so you start with w = 5
, you end up with y = 6
. In other words, the effect of y++
got overridden by the y =
assignment.