JavaScript: Operators
An operand – is what operators are applied to. For instance, in the multiplication of
5 * 2
there are two operands: the left operand is5
and the right operand is2
. Sometimes, people call these “arguments” instead of “operands”.An operator is unary if it has a single operand. For example, the unary negation
-
reverses the sign of a number:An operator is binary if it has two operands.
Usually, the plus operator +
sums numbers.
But, if the binary +
is applied to strings, it merges (concatenates) them:
let s = "my" + "string";
alert(s); // mystring
Note that if one of the operands is a string, the other one is converted to a string too.
alert( '1' + 2 ); // "12"
alert( 2 + '1' ); // "21"
However, note that operations run from left to right. If there are two numbers followed by a string, the numbers will be added before being converted to a string:
alert(2 + 2 + '1' ); // "41" and not "221"
Other arithmetic operators work only with numbers and always convert their operands to numbers.
For instance, subtraction and division:
alert( 2 - '1' ); // 1
alert( '6' / '2' ); // 3
The plus +
exists in two forms: the binary form that we used above and the unary form. The unary plus or, in other words, the plus operator +
applied to a single value, doesn’t do anything to numbers. But if the operand is not a number, the unary plus converts it into a number.
// No effect on numbers
let x = 1;
alert( +x ); // 1
let y = -2;
alert( +y ); // -2
// Converts non-numbers
alert( +true ); // 1
alert( +"" ); // 0
The binary plus would add them as strings:
let apples = "2";
let oranges = "3";
alert( apples + oranges ); // "23", the binary plus concatenates strings
If we want to treat them as numbers, we need to convert and then sum them:
let apples = "2";
let oranges = "3";
// both values converted to numbers before the binary plus
alert( +apples + +oranges ); // 5
// the longer variant
// alert( Number(apples) + Number(oranges) ); // 5
If an expression has more than one operator, the execution order is defined by their precedence, or, in other words, the default priority order of operators.
Precedence
Name
Sign
…
…
…
16
unary plus
+
16
unary negation
-
14
multiplication
*
14
division
/
13
addition
+
13
subtraction
-
…
…
…
3
assignment
=
…
…
…
As we can see, the “unary plus” has a priority of 16
which is higher than the 13
of “addition” (binary plus). That’s why, in the expression "+apples + +oranges"
, unary pluses work before the addition.
Let’s note that an assignment =
is also an operator. It is listed in the precedence table with the very low priority of 3
.
That’s why, when we assign a variable, like x = 2 * 2 + 1
, the calculations are done first and then the =
is evaluated, storing the result in x
.
let x = 2 * 2 + 1;
alert( x ); // 5
It is possible to chain assignments:
let a, b, c;
a = b = c = 2 + 2;
alert( a ); // 4
alert( b ); // 4
alert( c ); // 4
Chained assignments evaluate from right to left. First, the rightmost expression 2 + 2
is evaluated and then assigned to the variables on the left: c
, b
and a
. At the end, all the variables share a single value.
The result of a % b
is the remainder of the integer division of a
by b
.
alert( 5 % 2 ); // 1 is a remainder of 5 divided by 2
alert( 8 % 3 ); // 2 is a remainder of 8 divided by 3
alert( 6 % 3 ); // 0 is a remainder of 6 divided by 3
For a natural number b
, the result of a ** b
is a
multiplied by itself b
times.
alert( 2 ** 2 ); // 4 (2 * 2)
alert( 2 ** 3 ); // 8 (2 * 2 * 2)
alert( 2 ** 4 ); // 16 (2 * 2 * 2 * 2)
The operator works for non-integer numbers as well.
alert( 4 ** (1/2) ); // 2 (power of 1/2 is the same as a square root, that's maths)
alert( 8 ** (1/3) ); // 2 (power of 1/3 is the same as a cubic root)
Increment
++
increases a variable by 1:let counter = 2; counter++; // works the same as counter = counter + 1, but is shorter alert( counter ); // 3
Decrement
--
decreases a variable by 1:let counter = 2; counter--; // works the same as counter = counter - 1, but is shorter alert( counter ); // 1
Increment/decrement can only be applied to variables. Trying to use it on a value like 5++
will give an error.
The operators ++
and --
can be placed either before or after a variable.
When the operator goes after the variable, it is in “postfix form”:
counter++
.The “prefix form” is when the operator goes before the variable:
++counter
.
Both of these statements do the same thing: increase counter
by 1
.
If the result of increment/decrement is not used, there is no difference in which form to use:
let counter = 0; counter++; ++counter; alert( counter ); // 2, the lines above did the same
If we’d like to increase a value and immediately use the result of the operator, we need the prefix form:
let counter = 0; alert( ++counter ); // 1
If we’d like to increment a value but use its previous value, we need the postfix form:
let counter = 0; alert( counter++ ); // 0
Bitwise operators treat arguments as 32-bit integer numbers and work on the level of their binary representation.
The list of operators:
AND (
&
)OR (
|
)XOR (
^
)NOT (
~
)LEFT SHIFT (
<<
)RIGHT SHIFT (
>>
)ZERO-FILL RIGHT SHIFT (
>>>
)
This notation can be shortened using the operators +=
and *=
:
let n = 2;
n += 5; // now n = 7 (same as n = n + 5)
n *= 2; // now n = 14 (same as n = n * 2)
alert( n ); // 14
Short “modify-and-assign” operators exist for all arithmetical and bitwise operators: /=
, -=
, etc.
Such operators have the same precedence as a normal assignment, so they run after most other calculations:
let n = 2;
n *= 3 + 5;
alert( n ); // 16 (right part evaluated first, same as n *= 8)
The comma operator allows us to evaluate several expressions, dividing them with a comma ,
. Each of them is evaluated but only the result of the last one is returned.
let a = (1 + 2, 3 + 4);
alert( a ); // 7 (the result of 3 + 4)
Sometimes, people use it in more complex constructs to put several actions in one line.
For example:
// three operations in one line
for (a = 1, b = 3, c = a * b; a < 10; a++) {
...
}
Such tricks are used in many JavaScript frameworks. That’s why we’re mentioning them. But usually they don’t improve code readability so we should think well before using them.
Last updated