What is Destructuring?
Destructuring is a convenient way to extract values from arrays or properties from objects and assign them to variables in a single statement. It reduces boilerplate and makes code more readable.
| Feature | Use Case | Example |
|---|---|---|
| Array Destructuring | Extract array elements | const [a, b] = arr; |
| Object Destructuring | Extract object properties | const { name, age } = obj; |
| Default Values | Handle missing data | const { x = 0 } = obj; |
| Rest in Destructuring | Collect remaining items | const [first, ...rest] = arr; |
| Spread Operator | Expand arrays/objects | const merged = [...arr1, ...arr2]; |
| Rest Parameters | Capture function arguments | function fn(...args) {} |
| Renaming | Assign different names | const { name: n } = obj; |
Destructuring and spread/rest operators are essential modern JavaScript features that make code cleaner, more concise, and easier to maintain!
Array Destructuring
Basic Array Destructuring
Extract elements from an array into separate variables.
const colors = ["red", "green", "blue"];
// Without destructuring
const first = colors[0];
const second = colors[1];
// With destructuring
const [firstColor, secondColor] = colors;
console.log(firstColor); // "red"
console.log(secondColor); // "green"
Skipping Elements
Use commas to skip unwanted elements.
const [red, , blue] = ["red", "green", "blue"];
console.log(red); // "red"
console.log(blue); // "blue"
Default Values
Assign default values when elements might be undefined.
const [a, b, c = "default"] = [1, 2];
console.log(a); // 1
console.log(b); // 2
console.log(c); // "default"
Rest Element in Arrays
Use the rest operator (...) to collect remaining elements into an array.
const [first, ...rest] = [1, 2, 3, 4, 5];
console.log(first); // 1
console.log(rest); // [2, 3, 4, 5]
Swapping Variables
Destructuring makes variable swapping simple.
let x = 10;
let y = 20;
[x, y] = [y, x];
console.log(x); // 20
console.log(y); // 10
Destructuring in Function Parameters
Extract array elements directly in function parameters.
function printCoordinates([x, y]) {
console.log(`X: ${x}, Y: ${y}`);
}
printCoordinates([5, 10]); // "X: 5, Y: 10"
Object Destructuring
Basic Object Destructuring
Extract properties from an object into variables.
const person = {
name: "Alice",
age: 30,
city: "London"
};
// Without destructuring
const name = person.name;
const age = person.age;
// With destructuring
const { name, age } = person;
console.log(name); // "Alice"
console.log(age); // 30
Renaming Properties
Assign different variable names to properties.
const person = { firstName: "Bob", lastName: "Smith" };
const { firstName: fName, lastName: lName } = person;
console.log(fName); // "Bob"
console.log(lName); // "Smith"
Default Values
Set default values for missing properties.
const person = { name: "Carol" };
const { name, age = 25, city = "Unknown" } = person;
console.log(name); // "Carol"
console.log(age); // 25
console.log(city); // "Unknown"
Rest Properties
Collect remaining properties into a new object.
const user = {
id: 1,
name: "David",
email: "david@example.com",
role: "admin"
};
const { id, name, ...metadata } = user;
console.log(id); // 1
console.log(name); // "David"
console.log(metadata); // { email: "david@example.com", role: "admin" }
Nested Object Destructuring
Extract values from nested objects.
const person = {
name: "Eve",
address: {
city: "Paris",
country: "France"
}
};
const { name, address: { city, country } } = person;
console.log(name); // "Eve"
console.log(city); // "Paris"
console.log(country); // "France"
Destructuring in Function Parameters
Extract object properties directly in function parameters.
function displayUser({ name, age, email = "no-email" }) {
console.log(`${name}, ${age}, ${email}`);
}
displayUser({ name: "Frank", age: 35 });
// "Frank, 35, no-email"
Destructuring with Dynamic Keys
Use computed property names (advanced pattern).
const obj = { a: 1, b: 2 };
const key = "a";
const { [key]: value } = obj;
console.log(value); // 1
The Spread Operator (...)
The spread operator expands iterables (arrays, strings, objects) into individual elements.
Spreading Arrays
Combine multiple arrays into one.
const arr1 = [1, 2, 3];
const arr2 = [4, 5, 6];
const combined = [...arr1, ...arr2];
console.log(combined); // [1, 2, 3, 4, 5, 6]
Insert elements at specific positions.
const arr = [1, 5];
const withInserted = [1, 2, 3, ...arr, 4];
console.log(withInserted); // [1, 2, 3, 1, 5, 4]
Copying Arrays
Create a shallow copy of an array.
const original = [1, 2, 3];
const copy = [...original];
copy.push(4);
console.log(original); // [1, 2, 3]
console.log(copy); // [1, 2, 3, 4]
Spreading Strings
Convert a string into an array of characters.
const str = "hello";
const chars = [...str];
console.log(chars); // ["h", "e", "l", "l", "o"]
Spreading Objects
Merge multiple objects.
const obj1 = { a: 1, b: 2 };
const obj2 = { c: 3, d: 4 };
const merged = { ...obj1, ...obj2 };
console.log(merged); // { a: 1, b: 2, c: 3, d: 4 }
Overwrite properties with later values.
const defaults = { theme: "light", fontSize: 14 };
const userSettings = { theme: "dark" };
const finalSettings = { ...defaults, ...userSettings };
console.log(finalSettings); // { theme: "dark", fontSize: 14 }
Create a shallow copy of an object.
const original = { name: "Grace", age: 28 };
const copy = { ...original };
copy.age = 30;
console.log(original.age); // 28
console.log(copy.age); // 30
Spreading Function Arguments
Pass array elements as individual arguments to a function.
function sum(a, b, c) {
return a + b + c;
}
const numbers = [1, 2, 3];
console.log(sum(...numbers)); // 6
The Rest Operator (...)
The rest operator collects multiple elements into a single variable (typically an array or object).
Rest Parameters in Functions
Capture remaining arguments as an array.
function greet(greeting, ...names) {
names.forEach(name => console.log(`${greeting}, ${name}!`));
}
greet("Hello", "Alice", "Bob", "Carol");
// "Hello, Alice!"
// "Hello, Bob!"
// "Hello, Carol!"Rest in Array Destructuring
Collect remaining elements.
const [first, second, ...rest] = [10, 20, 30, 40, 50];
console.log(first); // 10
console.log(second); // 20
console.log(rest); // [30, 40, 50]
Rest in Object Destructuring
Collect remaining properties.
const { id, name, ...details } = {
id: 1,
name: "Henry",
email: "henry@example.com",
phone: "555-1234"
};
console.log(id); // 1
console.log(name); // "Henry"
console.log(details); // { email: "henry@example.com", phone: "555-1234" }
Practical Examples
Extract Function Parameters
function createUser(userData) {
const { name, email, ...profile } = userData;
console.log(`User: ${name}`);
console.log(`Email: ${email}`);
console.log(`Profile data:`, profile);
}
createUser({
name: "Iris",
email: "iris@example.com",
age: 26,
country: "Germany"
});
// User: Iris
// Email: iris@example.com
// Profile data: { age: 26, country: "Germany" }
API Response Handling
async function fetchUserAndPosts(userId) {
try {
const response = await fetch(`/api/users/${userId}`);
const { user: { name, email }, posts = [] } = await response.json();
console.log(`${name} (${email}) has ${posts.length} posts`);
} catch (error) {
console.log("Error:", error.message);
}
}
Array Filtering with Destructuring
const users = [
{ id: 1, name: "Jack", active: true },
{ id: 2, name: "Kate", active: false },
{ id: 3, name: "Liam", active: true }
];
const activeUsers = users
.filter(({ active }) => active)
.map(({ id, name }) => ({ id, name }));
console.log(activeUsers);
// [{ id: 1, name: "Jack" }, { id: 3, name: "Liam" }]
Function Composition with Spread
function multiply(a, b, c) {
return a * b * c;
}
function applyMultiply(...args) {
return multiply(...args);
}
console.log(applyMultiply(2, 3, 4)); // 24
Removing Duplicates from Array
const numbers = [1, 2, 2, 3, 3, 3, 4];
const unique = [...new Set(numbers)];
console.log(unique); // [1, 2, 3, 4]
Cloning Nested Objects (Shallow)
const original = {
name: "Monica",
skills: ["JavaScript", "React"]
};
const cloned = { ...original };
cloned.skills.push("Node.js");
console.log(original.skills); // ["JavaScript", "React", "Node.js"] (shared reference!)
Creating New Objects Without Mutation
const user = { name: "Noah", age: 32, role: "user" };
// Promote user to admin without mutating original
const admin = { ...user, role: "admin" };
console.log(user); // { name: "Noah", age: 32, role: "user" }
console.log(admin); // { name: "Noah", age: 32, role: "admin" }
Combining Destructuring and Rest
const [head, ...tail] = [1, 2, 3, 4, 5];
const { name, ...rest } = { name: "Olivia", city: "NYC", age: 29 };
console.log(head); // 1
console.log(tail); // [2, 3, 4, 5]
console.log(name); // "Olivia"
console.log(rest); // { city: "NYC", age: 29 }
Common Pitfalls
Shallow Copy Limitation
Spreading only creates a shallow copy — nested objects are still shared.
const original = { user: { name: "Peter" } };
const copy = { ...original };
copy.user.name = "Paul";
console.log(original.user.name); // "Paul" (shared reference!)
Solution: Use structuredClone() for deep copies.
const deepCopy = structuredClone(original);
deepCopy.user.name = "Paul";
console.log(original.user.name); // "Peter" (unchanged)
Rest Must Be Last
The rest operator must be the final element in destructuring.
// ✗ Invalid
const { ...rest, name } = obj;
// ✓ Valid
const { name, ...rest } = obj;
Order Matters in Rest
Only one rest element is allowed per destructuring.
// ✗ Invalid
const [a, ...b, ...c] = [1, 2, 3];
// ✓ Valid
const [a, ...rest] = [1, 2, 3];
Best Practices
Use destructuring for cleaner code — Extract needed values upfront.
Provide sensible defaults — Use
= defaultValuesyntax.Rename properties when needed — Use
{ prop: newName }for clarity.Combine with rest operator — Separate specific values from the rest.
Be aware of shallow copying — Use
structuredClone()for deep copies.Use spread in function calls — Avoid manual array unpacking.
Prefer destructuring in parameters — Makes function contracts clearer.
Keep destructuring readable — Don't over-nest or create overly complex patterns.
Use rest parameters — Instead of
argumentsobject in modern JavaScript.Comment complex destructuring — Help future readers understand intent.