DEV Community

Cover image for Mastering the JavaScript Reduce method ✂️
sanderdebr
sanderdebr

Posted on

Mastering the JavaScript Reduce method ✂️

JavaScript roughly has 30 built-in methods for manipulating arrays. Chances are that you are probably using map(), filter() or e.g. forEach() quite often. But how often do you use the reduce() method?

The reduce method is, in my opinion, the most powerful array method of JavaScript. For me it was unclear how this method exactly works for quite some time so in this article we will reveal the power of the reduce method! 😄


The basis

The reduce method always returns a single value, which is in contrast to map() and filter() which return a new array with one or more values.

It takes four arguments, but most of the time you'll only need the first two.

  1. accumulator (often called acc)
  2. current value (often called cur)
  3. current index
  4. source array

Let's say we have a list of scores and we want to display the sum of all scores. We could create a for-loop and count them in a new variable called total:

const scores = [23,63,23,35];
let total = 0;
for (i = 0; i < scores.length; i++) {
  total += scores[i];
}
console.log(total); // 144

Reduce makes this much easier. We give it a reducer function, that applies some action on every item in the given array, and an initial value from where we want to start (in this case 0).

const scores = [23,63,23,35];
const reducer = (acc, cur) => acc + cur;
const total = scores.reduce(reducer, 0);
console.log(total); // 144

We can refactor this to:

const scores = [23,63,23,35];
const total = scores.reduce((acc, cur) => acc + cur, 0);
console.log(total); // 144

Awesome! Let's continue.


Flattening an array

Let's say we have an array with multiple arrays inside:

let arrays = [[1, 2, 3], [4, 5], [6]];

and we want to convert this into one single array. How can we do this with reduce? We need to link together a.k.a. concatenate every array together, so we'll use concat() on every item and we'll set our initial value as an array:

const flatten = arrays => arrays.reduce((acc, curr) => acc.concat(curr), []);
flatten(arrays); // [1, 2, 3, 4, 5, 6]

Yay! Let's do another one. 😃


Splitting values of two given arrays into two groups

Let's say we receive two arrays: one with a list of numbers and one with a list of true/false values and we want to filter the first list of numbers based on their true/false value.

[1, 2, 3, 4], [true, true, false, true];

Another thing we can do easily with reduce! For our initial value, we'll set an array containing two empty arrays. We will apply the reduce method on the numbers array.

const splitTrueFalse = (arr, filter) => arr.reduce((acc, cur) => ... ,[[],[]]);

Remember the reduce method takes a third argument, the index? We will use the index to determine if the values is true or false based on the second array.

We'll push the current number in the the first array if its value in the filter array is true by checking filter[i] ? 1 : 0. We'll return our acc array so we can keep push values to it.

const splitTrueFalse = (arr, filter) => arr.reduce((acc, cur, i) => {
  acc[filter[i] ? 1 : 0].push(cur);
  return acc;
} ,[[],[]]);

We can refactor our code by returning acc in one line:

 const splitTrueFalse = (arr, filter) => arr.reduce((acc, cur, i) => (acc[filter[i] ? 0 : 1].push(cur), acc), [[], []]);

Cool! Let's make it a bit more difficult. 😎


Creating an object from given key-value pairs.

In this example we'll receive an array containing multiple arrays, each with a key-value pair.

const pairs = [['name', 'Sander'], ['age', 26], ['likes', 12]];

With reduce we can easily convert this to an object. First we'll set our initial value as an object, which we will fill it with every iteration.

const arrToObject = arr => arr.reduce((acc, cur) => ... , {});

Next up we'll have to convert each array to a key-value pair inside our object.
The key we can get by grabbing the first value inside our array: cur[0]
By using bracket notation we can set our key to a string value: acc[cur[0]].

The value we'll get by grabbing the second item in the current array: cur[1].
As in the example before, we return our acc accumulated value every time so we can build upon our object.

const arrToObject = arr => arr.reduce((acc, cur) => (acc[cur[0]] = cur[1], acc) , {});

Hope you have a better understanding of the awesome reduce method!

Make sure to follow me for more tips and tricks. 🧠

Discussion (0)