The Nullish Coalescing Operators
Behind this funny name lies a powerful operator that can simplify our code considerably.
You may be familiar with the conditional ternary operator (a ? b : c
), but there’s a lesser known binary operator (a ?? b
) that simplifies cases where the value of one parameter is used as a fallback for another.
The nullish coalescing operator (??
) takes two values and returns the first one if it’s not null
or undefined
, or the second one otherwise:
let a = b ?? c;
With the ternary operator notation it would be:
let a = (b !== null && b !== undefined) ? b : c;
Which is equivalent to:
let a;
if (b !== null && b !== undefined) {
a = b;
} else {
a = c;
}
A significant improvement in code length and readability.
Nullish vs Falsy
This operator relies on the difference between falsy and nullish. In JavaScript, there are many values that will evaluate to false
in a conditional statement: null
, undefined
, 0
, false
, NaN
... (among others) these values are considered “falsy.”
Many falsy values can be the result of an operation (e.g., 1–1=0
), but two of them (null
and undefined
) indicate that there’s something missing: maybe they were not defined/declared or maybe a value was not assigned yet. These two are called “nullish.”
Nullish values are always falsy, but falsy values may not be nullish. The nullish coalescing operator takes this into account, making it extremely helpful with methods and APIs that return a value of zero or false
, which may be falsy but is valid.
If we want to take into consideration the falsy values, we could use the ||
operator instead:
let a = 0;
let b = 1;
console.log(a || b); // 1 because 0 is falsy
console.log(a ?? b); // 0 because 0 is not nullish
Nullish Coalescing Assignment (??=)
The nullish coalescing operator can be combined with the =
operator to simplify assignments. It assigns a value only if the variable that we are assigning to is null
or undefined
(nullish).
let a = 1;
let b = 2;
let c = 3;
a ??= b; // `a` will be 1 as it already had a value
a = undefined;
a ??= c; // `a` will be 3 as it was nullish
This type of assignment can be incredibly useful when working with objects or parameters. For example, if we want to assign a property if, and only if, it hasn’t been instantiated yet:
const car = { doors: 4 };
car.speed ??= 65; // car.speed is 65, because it was undefined
car.doors ??= 2; // car.doors is 4, as it was already defined