What's the Spread Operator Used For in JavaScript?
Practical guide to the JavaScript spread operator: syntax, array and object examples, merging, function arguments, strings, rest vs spread, shallow-copy caveats, and best practices.
Drake Nguyen
Founder · System Architect
Introduction to the JavaScript spread operator
The javascript spread operator (often written as three dots: ...) is an ES6 feature that expands the elements of an iterable—such as arrays, strings, or the enumerable properties of objects—into places where zero or more values are expected. The spread syntax is compact and expressive, making common tasks like copying arrays, merging objects, and passing array elements as function parameters straightforward.
The basics of spread syntax
At its core, the spread operator extracts items from an iterable and inserts them into a new context. When used inside an array literal or object literal it spreads the contents into that new structure.
// Copy an array
const greetings = ['hello', 'bonjour', 'konnichiwa'];
const copy = [...greetings];
console.log(copy); // ['hello', 'bonjour', 'konnichiwa']
// The spread operator must appear inside a literal or call site
// ...greetings by itself (outside of an array/object/function) is a syntax error
Duplicating iterable objects
The es6 spread operator is a concise way to duplicate arrays and object literals. It creates a new top-level container and copies enumerable items or properties into it.
// Array copy
const arr = [1, 2, 3];
const arrCopy = [...arr];
// Object copy
const obj = { english: 'hello', french: 'bonjour' };
const objCopy = { ...obj };
console.log(arrCopy); // [1, 2, 3]
console.log(objCopy); // { english: 'hello', french: 'bonjour' }
Note: the spread operator performs a shallow copy. Nested objects or arrays remain referenced to the original (see the Caveats section).
Merging arrays and objects
Use the spread operator to merge multiple iterables into one. This is often clearer than using methods like concat or Object.assign.
// Merge arrays
const a = ['a', 'b'];
const b = ['c', 'd'];
const merged = [...a, ...b, 'e'];
console.log(merged); // ['a', 'b', 'c', 'd', 'e']
// Merge objects (later properties overwrite earlier ones)
const base = { english: 'hello', french: 'bonjour' };
const extras = { english: 'howdy', german: 'gutentag' };
const combined = { ...base, ...extras, spanish: 'hola' };
console.log(combined);
// { english: 'howdy', french: 'bonjour', german: 'gutentag', spanish: 'hola' }
When merging objects, the property order determines which values win: properties from later spreads overwrite previous ones.
Feeding arguments into functions
The spread operator can replace Function.prototype.apply when you want to pass an array as separate arguments to a function. This makes calling functions with an array of values simpler and more readable.
function calcVolume(width, height, depth) {
return width * height * depth;
}
const dims = [12, 30, 14];
// Old approach: calcVolume.apply(null, dims)
const volume = calcVolume(...dims);
console.log(volume);
Spread operator with strings
Strings are iterable in JavaScript, so the spread syntax can expand a string into individual characters. This is handy when you need an array of characters or when combining letters with other iterables.
const name = 'jumanji';
const letters = [...name];
console.log(letters); // ['j', 'u', 'm', 'a', 'n', 'j', 'i']
Rest vs spread operator
Although they share the same three-dot notation, the rest operator and spread operator serve opposite purposes:
- Spread: expands an iterable into individual elements (used in array/object literals and call sites).
- Rest: collects multiple function arguments or remaining array elements into a single array (used in function parameters or destructuring).
// Spread (call site)
const nums = [1, 2, 3];
Math.max(...nums); // expands to Math.max(1, 2, 3)
// Rest (parameter)
function sum(...values) {
return values.reduce((s, v) => s + v, 0);
}
sum(1, 2, 3); // values is [1, 2, 3]
Caveats and common pitfalls
Keep these important details in mind when using the spread operator in JavaScript:
- Shallow copy: Spread copies only the first level. Nested arrays or objects still reference the same inner objects (spread operator shallow copy javascript).
- Type differences: Spreading an array or string into an object literal will create numeric keys for indexes; results may be unexpected when mixing types.
- Overwriting properties: When merging objects, later properties overwrite earlier ones (merge objects using spread operator javascript).
- Performance: For very large arrays or objects, spreading can be memory-intensive compared to more targeted strategies.
// Shallow copy example
const nested = { a: { x: 1 } };
const shallow = { ...nested };
shallow.a.x = 42;
console.log(nested.a.x); // 42 — inner object was not deeply cloned
Further reading and examples
To practise, try tasks such as: copying arrays with the spread operator, merging arrays with spread operator javascript, passing an array as function arguments using spread operator, and copying objects with the spread operator. For authoritative documentation and edge cases consult MDN and ECMAScript 2015 (ES6) resources.
Conclusion
The javascript spread operator is a versatile ES6 feature that simplifies working with iterables: copying and merging arrays and objects, spreading strings into characters, and passing arrays as function arguments. Understanding its shallow-copy behavior and differences from the rest operator will help you use it correctly and avoid common mistakes.