stackademic

The leading education platform for anyone with an interest in software development.

JavaScript Spread and Rest

Expand iterables with spread and collect remaining values with rest

Overview

The ... operator has two roles: spread expands arrays or objects into individual elements; rest collects remaining items into a new array or object. Same syntax, different positions.

Syntax / Usage

// Spread — arrays
const a = [1, 2]
const b = [...a, 3, 4]  // [1, 2, 3, 4]

// Spread — objects (shallow)
const base = { a: 1, b: 2 }
const extended = { ...base, b: 99, c: 3 }

// Rest — function parameters
function sum(first, ...numbers) {
  return numbers.reduce((t, n) => t + n, first)
}

// Rest — destructuring
const [head, ...tail] = [1, 2, 3, 4]
const { id, ...fields } = { id: 1, name: 'Ada', role: 'dev' }

Examples

Clone and update state immutably:

setUser((prev) => ({ ...prev, name: 'New Name' }))
setItems((prev) => [...prev, newItem])

Merge configuration objects:

const defaults = { retries: 3, timeout: 5000 }
const userOpts = { timeout: 10000 }
const config = { ...defaults, ...userOpts }

Common Mistakes

  • Expecting deep clone from spread—it is shallow only one level
  • Spreading undefined in object literals is a no-op; spreading undefined in arrays throws
  • Overusing spread on large arrays where performance matters
  • Using rest without it being the final element in destructuring

See Also

destructuring arrays objects array-methods