Skip to content

Instantly share code, notes, and snippets.

@jefflau
Last active October 3, 2015 10:09
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save jefflau/36dc22f2fe7dc3492850 to your computer and use it in GitHub Desktop.
Save jefflau/36dc22f2fe7dc3492850 to your computer and use it in GitHub Desktop.
A journey through ES6 - Part 3

#Destructuring

Destructuring is a very useful technique in ES6. It allows you to 'break down' or 'deconstruct' an object into variables. Think of it like flattening the object so all the properties and value come out as normal variables.

##Simple Example

var obj = {
  a: 1,
  b: 2,
}

//without destructuring
var a = obj.a;
var b = obj.b;

//with destructuring
var {a, b} = obj

a; //1
b; //2

A practical example of using destructuring is when passing an object as options to a function. For instance if you were setting up a slider that might have a lot of options, you would want to pass an options object instead of arguments. This would create a cleaner API so you don't need to remember the position of the parameters in your slider. This is where destructuring is a perfect fit.

##Simple Practical Example

//ES5
function setupSlider(options) {
  var type = options.type,
      transition = options.transition, 
      slides = options.slides, 
      hasThumbnails = options.thumbnails;
  
  console.log(type, transition, slides, hasThumbnails);
  // "hero", "slide-left", { ... }, false
}

//ES6
function setupSlider(options) {
  var {type, transition, slides, hasThumbnails} = options;
  
  console.log(type, transition, slides, hasThumbnails);
  // "hero", "slide-left", { ... }, false
}

setupSlider({
  type: "hero",
  transition: "slide-left",
  slides: { ...},
  hasThumbnails: false,
});

You can also destructure straight into the function parameters so you make even more concise and get rid of the options argument entirely.

##Simple Practical Example 2

function setupSlider({type, transition, slides, hasThumbnails}) {

  console.log(
    type, // "hero"
    transition,  // "slide-left"
    slides, // { ... }
    hasThumbnails // false
  );
  
}

setupSlider({
  type: "hero",
  transition: "slide-left",
  slides: { ...},
  hasThumbnails: false,
})

##Destructuring Arrays Destructuring is not just limited to objects either, you can also destructure arrays.

var array = ["one", "two", "three"];

// without destructuring
var a = array[0];
var b = array[1];
var c = array[2];

// with destructuring
var [a, b, c] = awesome;

##Returning multiple values from a function Similar to the practical example before, you can destructure return values whether they are object or arrays and easily destructure them in one statement.

//with arrays
function awesome() {
  //does some awesome stuff and then returns an array
  return [1, 2, 3];
}

var [a, b, c]  = awesome();

//with objects
function awesome() {
  //does some awesome stuff and then returns an array
  return {
    a: 1, 
    b: 2, 
    c: 3
  };
}

var {a, b, c}  = awesome();

##Changing the variable names It would seem so far that you can only destructure objects with the same variables names as the property names, but actually you an assign whatever names you want, but you need to use a slightly longer syntax.

var obj = {
  a: 1, 
  b: 2, 
  c: 3
}
//long syntax
var {a: a, b: b, c: c} = obj;

What's confusing now is which one is the variable name and which one is the property name in the object? Well, if you think of it like a normal object {a: 42}. The property name in the object when destructuring never moves. So you would place the rename where the value would usually be so var {a: newName} = {a: 42} would create a variable newName with the same value as the property a inside the object. Therefore to destructure the last object with a different name you can do this:

var obj = {
  a: 1, 
  b: 2, 
  c: 3
}

var {a: iLikeCake, b: soDoI, c: andMeToo} = obj;

console.log(iLikeCake, soDoi, andMeToo); // 1, 2, 3

If you remember the name of the property never moves, you shouldnt have a problem remembering how the long version works! I don't use this that often, but it might be useful for creating a new object from an old object and changing the names where they don't make sense.

##Default values

We can also create default value assignments for a variable that might not exist on the object.

var obj = {
  a: 1, 
  b: 2, 
  c: 3
}

var {a, b, c = 30, d = 40} = obj;

console.log(a, b, c, d) // 1, 2, 3, 40

##Slightly more advanced practical example

function getProductImages() {
  //some code that gets an object of images
  return {
    name: 'aardvark',
    createdDate: new Date(),
    small: 'http://placehold.it/250x250',
    medium: 'http://placehold.it/500x500',
    large: 'http://placehold.it/1000x1000'
  }
}

function displaySmallProductImage(){
  var {name, createdDate, small: url} = getProductImages()
  console.log(name, createdDate, url);
  //do some stuff to display this
}

displaySmallProductImage();

In this example we have a two functions, the displaySmallProduct function goes and gets the productImages for that particular product, the function returns an object that contains more values than we need about the medium and large images. So when we destructured the object, we simply omitted those values. The name and createdDate make sense for this example and therefore we use the short syntax where it will match the name for us. However this particular case we should change the name from small to something more relevant such as url, so make the code more readable so instead of {name, createdDate, small}, we can write the long syntax just for small so we get {name, createdDate, small: url}.

##Wrapping Up

Destructuring is super useful in its simplest form, especially for option type objects and for readability. It is also very powerful and you can also start to destructure nested objects and arrays, but once you start mixing the short and long syntax, changing variable names, it starts to become harder and harder to read.

//Eg
var product = { 
  a: "chair", 
  b: { 
    productInfo: { 
      slides: ["image1", "image2", "image3"]
    }
  }
};

//With Destructuring
var {
  productName: name,
  productInfo: {
    slides: {
      images: [ , , image3] //you can omit array values by adding commars
    }
  }
} = product;
console.log(name, image3);

//without Destructuring
var name = product.name,
    image3 = product.productInfo.slides[2];

I've written about practical examples that I use everyday, but there's a lot more to destructuring that you can learn. The last example I gave I would not use destructuring as to even make it remotely readable you need to indent it, and its also a lot more typing and still less readable. Once you've learnt how destructuring works it can be easy to go overboard and destructure absolutely everything, but you might be the only one able to read it, so use it only when it makes sense!

##References and Further Reading

https://developer.mozilla.org/en/docs/Web/JavaScript/Reference/Operators/Destructuring_assignment https://hacks.mozilla.org/2015/05/es6-in-depth-destructuring/

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment