DEV Community

Christian Fields
Christian Fields

Posted on

ES6 {Destructuring} Deep Dive

We all know what variables are, and there are plenty of times where we find ourselves using objects or arrays with long property names on them over, and over, and over... Wouldn't it be nice to just have a variable referring to that property without assigning fifty variables manually? Well, that's where destructuring comes in - destructuring is a way of saving values from complex data types to a variable without having to make a bunch of them by hand.

Basics of Destructuring

The basic syntax for destructuring is pretty simple, but a lot of people don't know how to use it, so let's go over a couple examples with both objects and arrays! We'll do this with the destructuring "binding" pattern, though there's also an "assignment" pattern. We can start with a basic object:

const obj = {
  a: 1,
  two: 83,
  banana: 'bread',
}
Enter fullscreen mode Exit fullscreen mode

To "destructure" this object, we essentially just assign variables to it using object syntax!

// this grabs the "two" property and the "banana" property
// from our object, but not our "a" property
// this is great for when we need to reuse a value repeatedly,
// like if you were using props in React!
const { two, banana } = obj;

// and then we can access our destructured values
// like any other variable!
console.log(two); // outputs 83 to the console
console.log(banana); // outputs "bread" to the console
Enter fullscreen mode Exit fullscreen mode

Arrays have a similar destructuring syntax, but will assign values in order instead of by a key name, since they don't have the same kinds of keys an object does:

const arr = [1, 2, 3, 4, 5]
const [a, b, c] = arr;
// a = 1, b = 2, c = 3!
Enter fullscreen mode Exit fullscreen mode

So, those are the basics! But what if we wanted to get a bit more in-depth? Maybe we don't want to assign variables to EVERY value, but still want ongoing access to the remaining values separate from the original collection?

...Destructuring and the Spread Operator

We can actually use the spread operator with both arrays and objects to "scoop up" the remaining values into a neat little array/object separate from the original one! For arrays, the result is simple enough:

const groceries = ["spaghetti", "tomatoes", "milk", "butter", "cheese"];
const [pasta, fruit, ...dairy] = groceries;
// "pasta" holds "spaghetti",
// and "fruit" holds "tomatoes", just like before,
// but now we have access to a "dairy" array
// which looks like this: ["milk", "butter", "cheese"]
Enter fullscreen mode Exit fullscreen mode

Cool, right? Objects are pretty much the same, but instead save the results to a new object with the remaining properties on it:

const zeldaQuotes = {
  dekuScrub: "Twenty-three is number one!",
  link: "Hyah! Hup! Ha! Hyah!",
  navi: "Hey, listen!",
  zelda: "Help me, Link! You're my only hope! Wait, wrong franchise..."
};

const { link, navi, ...rest } = zeldaQuotes;

console.log(link); // outputs "Hyah! Hup! Ha! Hyah!"
console.log(navi); // outputs "Hey, listen!"
console.log(rest);
// ^ outputs an object that looks like this:
// (I shortened the quotes for space)
// { dekuScrub: "...", zelda: "..." }
Enter fullscreen mode Exit fullscreen mode

Notice how, with objects, we don't even need to grab the properties in order! We got link and navi, skipping dekuScrub entirely, but our rest variable still has both zelda AND our skipped dekuScrub!

Well, that's cool and all, but what are some other things we can do?

More cool stuff!

Nested Destructuring and Default Values

Well, what if maybe one of our values was undefined? That's when you'd use a default value. Just like with a function parameter, you can assign a "default" to a destructured variable in case the value is undefined! This is pretty easy:

// since b's value is undefined, it's automatically set to 12
// note: would not take effect if we used null instead of undefined
const { a, b = 12, c } = { a: 1, b: undefined, c: 18 };
Enter fullscreen mode Exit fullscreen mode

And if a value in an array or object is another array or object, we can nest destructuring syntax to get to these nested values more quickly and conveniently:

const obj = { a: 1, b: { c: 13 }, d: 9 };
const { a, b: { c }, d } = obj;
console.log(c); // outputs 13!
Enter fullscreen mode Exit fullscreen mode
const arr = [ 1, [ 13, 18 ], 12 ];
const [ a, [ b, c ], d ] = arr;

console.log(a, b, c, d); // outputs 1 13 18 12
Enter fullscreen mode Exit fullscreen mode

Reassignment

If we want to reassign destructured values, we can simply use the let keyword instead of const! If we want some values to be reassignable and others not to be, we'd have to destructure multiple times:

const obj = { a: 1, b: 2, c: 3};
const { a, b } = obj;
let { c } = obj;

console.log(c); // outputs 3
c = 4;
console.log(c); // outputs 4!
a = 2 // TypeError: Assignment to constant variable :(
Enter fullscreen mode Exit fullscreen mode

Variable Swapping

With arrays and simple values, you can use destructuring to easily swap values! I personally found this really helpful in a function I wrote recently.

let pop = 'tart';
let tart = 'pop';
// outputs "tartpop"... that doesn't seem quite right...
console.log(pop + tart);

[pop, tart] = [tart, pop]; // basic destructuring swap!
console.log(pop + tart); // outputs "poptart" :D
Enter fullscreen mode Exit fullscreen mode
const arr = [ 1, 2, 3 ];
[arr[0], arr[1], arr[2]] = [arr[1], arr[2], arr[0]];
console.log(arr); // outputs [2, 3, 1]!
Enter fullscreen mode Exit fullscreen mode

Ignoring Values w/ Arrays and Function Destructuring

If you want to skip a value when destructuring an array, you can simply leave an empty space in its place:

const arr = [ 1, 2, 3 ];
const [ a, , b ];
// a = 1, b = 3, we don't need 2!
Enter fullscreen mode Exit fullscreen mode

Additionally, we can easily destructure function outputs, which is quite frequently used when working with React hooks! This is a bit of a silly example, but here's a basic showcase of destructuring the output of a function that returns an array:

function makeArr(...args) { return args; }
[a, b, c] = makeArr(1, 2, 3);
console.log(a, b, c); // outputs 1 2 3
Enter fullscreen mode Exit fullscreen mode

We can even destructure function parameters if we know what kinds of arguments we'll get, which I personally use a lot with both imports and when passing values through props with React!

function logProperties({ a, b, c }) {
  console.log(a, b, c);
}

logProperties({ a: 1, b: 2, c: 3 }); // outputs 1 2 3
Enter fullscreen mode Exit fullscreen mode

Wrapping up...

That's most of the stuff on destructuring I could find that'd make sense to include. Destructuring is a surprisingly in-depth topic in and of itself, and on the MDN page alone I found quite a bit of info on them that I've already started integrating into my daily code usage. It's definitely been a more fun topic to look into than I thought it would be.

Top comments (0)