Pre increment in Javascript

javascript, pre-increment

Solution

From EcmaScript standard:

11.4.4 Prefix Increment Operator

The production UnaryExpression : ++ UnaryExpression is evaluated as follows:

- Let expr be the result of evaluating UnaryExpression.

- Throw a SyntaxError exception if the following conditions are all true: �

- Type(expr) is Reference is true

- IsStrictReference(expr) is true

- Type(GetBase(expr)) is Environment Record

- GetReferencedName(expr) is either "eval" or "arguments"

- Let oldValue be ToNumber(GetValue(expr)).

- Let newValue be the result of adding the value 1 to oldValue, using the same rules as for the + operator (see 11.6.3).

- Call PutValue(expr, newValue).

- Return newValue.

and

11.13.2 Compound Assignment ( op= )

The production AssignmentExpression : LeftHandSideExpression AssignmentOperator AssignmentExpression, where AssignmentOperator is @= and @ represents one of the operators indicated above, is evaluated as follows:

- Let lref be the result of evaluating LeftHandSideExpression.

- Let lval be GetValue(lref).

- Let rref be the result of evaluating AssignmentExpression.

- Let rval be GetValue(rref).

- Let r be the result of applying operator @ to lval and rval.

- Throw a SyntaxError exception if the following conditions are all true:

- Type(lref) is Reference is true

- IsStrictReference(lref) is true

- Type(GetBase(lref)) is Environment Record

- GetReferencedName(lref) is either "eval" or "arguments"

- Call PutValue(lref, r)

Thus, `var i = 0; i += ++i` is:

i = 0;
lvalue = value(i), which is 0;
rvalue = value(++i), which is: increment i, then value of i (1);
thus, rvalue = 1;
i = lvalue (0) + rvalue (1), which is 1.

Completely according to spec.

However, in C++, this is specifically defined to be undefined behaviour, thus on a different compiler you might also get 1. Or 99. Or it could set your computer on fire. All of those would be standard-compliant compilers. Thus, most people will recommend you only use pre/post-incremented variable once in a statement.

Problem

I've just encountered a 'feature' in Javascript regarding pre-increments. In all other languages I've used, it goes like I thought it would. E.g. in C++: ``` #include <iostream> int main() { int i = 0; i += ++i; std::cout << i << std::endl; // Outputs 2. } ``` So, `++i` doesn't make copy of the variable, hence the output is 2. Same in PHP: ``` <?php $i = 0; $i += ++$i; echo $i; // Outputs 2. ``` However, in Javascript: ``` var i = 0; i += ++i; console.log(i); // Outputs 1. ``` So it looks like that in Javascript, it makes copy of `i` and doesn't reference the variable. Is this intentional and if yes, why?

Original source

Related problems