Why doesn't the value of x
increment in the following code?
#include <stdio.h>
int main(){
int x = 3, i = 0;
do {
x = x++;
i++;
} while (i != 3);
printf("%d\n", x);
}
Why doesn't the value of x
increment in the following code?
#include <stdio.h>
int main(){
int x = 3, i = 0;
do {
x = x++;
i++;
} while (i != 3);
printf("%d\n", x);
}
In x = x++
, you are saying both to increment x
and to assign x
a value. The C standard does not define what happens if you do both of these things “at the same time.” For this purpose, “at the same time” means your code has not arranged for one of them to occur before the other.
If you put the increment and the assignment in separate statements, the C standard says that one of them occurs before the other, and then the behavior is fully defined. Technically, there is a sequence point between two such statements. Sequence points are barriers that separate effects. Inside the single statement x = x++
, there is no sequence point.
(There is more about sequence points and sequencing in C, but the details are beyond the scope of this question.)
In the simplest C implementation, the compiler might treat x = x++;
as if it were x = x; x++;
or as if it where int Temporary = x; x++; x = Temporary;
. The first would set x
to 3 and then to 4. The second would set x
to 4 and then to 3. However, the C standard gives implementations a great deal of latitude. In some C implementations, integer types might be made up of parts—a small computer might not be able to handle 32-bit integers all at once, so it might have to do arithmetic in multiple 16-bit steps, or even multiple 8-bit steps. The C standard says, since you have not arranged for the assignment and the increment to occur in a particular order, then, not only is the implementation allowed to do them in either order, it is even allowed to mix the steps. It might do one byte of the assignment, one byte of the increment, the second byte of the assignment, the second byte of the increment, the third byte of the increment, the third byte of the assignment, and so on. In general, you could get a nonsensical answer that is a mishmash of operations on the parts.
So the C standard does not say that, if you do not arrange for the operations to be ordered, then either one happens before the other. It says, if you do not arrange for the operations to be ordered, we do not guarantee what will happen at all. You may get a big mess.