public class Test
{
public static void main(String[] args) {
int i = 10;
i = i++;
System.out.println("value of i is : " + i);
}
}
Output is : 10
When I executed similar code in C
, output is 11
.
public class Test
{
public static void main(String[] args) {
int i = 10;
i = i++;
System.out.println("value of i is : " + i);
}
}
Output is : 10
When I executed similar code in C
, output is 11
.
With respect to C
this is undefined behavior since you are trying to modify the same variable more than once within the same sequence point on this line:
i = i++;
the draft C99 standard in section 6.5
paragraph 2 says:
Between the previous and next sequence point an object shall have its stored value modified at most once by the evaluation of an expression. Furthermore, the prior value shall be read only to determine the value to be stored.
This is well defined in Java, which does not have the same sequence point concept that C
does and the Java Language Specification(JLS) goes out of its way to ensure such operations are defined. Section 15.7 of the JLS says:
The left-hand operand of a binary operator appears to be fully evaluated before any part of the right-hand operand is evaluated. For example, if the left-hand operand contains an assignment to a variable and the right-hand operand contains a reference to that same variable, then the value produced by the reference will reflect the fact that the assignment occurred first. [...]
and section 15.7.2
says:
The Java programming language also guarantees that every operand of an operator (except the conditional operators &&, ||, and ? :) appears to be fully evaluated before any part of the operation itself is performed.
Note that C
does not specify the order of evaluation, mainly to give the compiler better options for optimization. From the draft standard section 6.5
paragraph 3:
The grouping of operators and operands is indicated by the syntax.74) Except as specified later (for the function-call (), &&, ||, ?:, and comma operators), the order of evaluation of subexpressions and the order in which side effects take place are both unspecified.
Update
If you want a discussion on some of the differences in philosophy between Java and C with respect undefined behavior you have Undefined behavior is a design decision and Undefined behaviour in Java.
This is Undefined behaviour in C
. Lack of sequence point.
In Java, i = i++;
post ++ will increment value after that step. But here at the moment of assigning i++
to i
, i
still is 10
so you are getting 10
. But in C this may different from Java. If you use i=++i
in Java
code, you will get 11.
Java and C are different languages with different rules. In C, the exact order in which expressions are evaluated and side effects are applied is unspecified; for an expression like i = i++
, there's no guarantee that the side effect of the ++
operator will be applied before the assignment takes place. The result will vary depending on the platform, optimization settings, even the surrounding code. The behavior is undefined; the compiler can handle the situation any way it sees fit, which includes generating an unexpected result.
Java, OTOH, does specify a strict order of evaluation and that side effects are applied immediately, so the expression is well-defined.