Get a Subset of an Object

Unpacking ES6

paul christophe

--

I saw this on Stack Overflow as a way to get the subset of an object:

const object = { a: 5, b: 6, c: 7  };const subset = (({ a, c }) => ({ a, c }))(object);console.log(subset); // { a: 5, c: 7 }

The second line might look confusing so let’s break it apart and see what’s going on. This is an exercise in JS, ES6, and functional programming.

IIFE

Start by looking at part of the second line:

const subset = ( ... )(object);

In order to understand this, let’s first create an example using ES6’s arrow function syntax. On the next line we’ll call that function by passing two variables.

const add = (a, b) => a + b;const sum = add(1, 2); // sum equals 3

We can make this more succinct by wrapping the function in parenthesis before calling it with variables.

const sum = ((a, b) => a + b)(1, 2) // sum equals 3

The function expression is evaluated then immediately called with the parenthesis at the end. This is called an IIFE or Immediately Invoked Function Expression.

Using our knowledge of IIFEs, we can break the function apart like this:

const getSubset = ({ a, c }) => ({ a, c });
const subset = getSubset(object);

Object Destructuring and Initializing

Next, let’s focus on the function being declared inside the IIFE.

({ a, c }) => ({ a, c })

You’ll see { a, c } is written twice. Although it looks redundant, both are performing two very different tasks.

Destructuring

The bold part below is object destructuring.

({ a, c }) => ({ a, c })

You can get specific variables from an object by using this syntax. For example, say I have a location object…

const location = { city: 'Brooklyn', state: 'NY', zip: 11221 };

… and I want to get a variable with just my ZIP code:

const { zip } = location;console.log(zip); 
// 11221

When this is used in a function the idea is the same:

const logZIP = ({ zip }) => {
console.log(zip);
};
logZip(location);
// 11221

Shorthand Object Initializing

The second part of the function is not destructuring but combining the variables a and c into a new object.

({ a, c }) => ({ a, c })

So for example, you could take a few variables and initialize them into a new object using ES6 syntax:

const city = 'Brooklyn';
const state = 'NY';
const zip = 11221;
const location = { city, state, zip };console.log(location);
// { city: 'Brooklyn', state: 'NY', zip: 11221 }

The first { a, c } in parenthesis is extracting the variables we want. The second is returning a new object with only a & c.

Returning the Object

Why not return the object without parenthesis?

({ a, c }) => { a, c } // this will throw an error

ES6 arrow functions parse curly brackets as a function block. For example these are equivalent:

(a, b) => a + b(a, b) => { return a + b }

In order for the javascript engine to interpret the curly brackets as a new object and not as a function block, we have to wrap the return value in a parenthesis.

... => ({ a, c })

Wrapping Up

// 1. IIFE
( ({ a, c }) => ({ a, c }) )(object)
// 2. Destructure object with only the values we want
(({ a, c }) => ({ a, c }))(object)
// 3. returning new object
(({ a, c }) => ({ a, c }))(object)

If you found this helpful be sure to 👏 clap👏 and leave comments below!

--

--