Encodera

Thanks for reading!

Donate to the site — we work hard for you.

Contents

map, filter and reduce

Most array tasks come down to three actions: change every element, pick the matching ones, or calculate a total. The methods map(), filter() and reduce() exist for exactly that. Code using them is shorter than a loop, and the method name tells you right away what it does.

map — transform every element

map() calls a function for each element and collects the results in a new array of the same length:

const numbers = [1, 2, 3];
 
const doubled = numbers.map((n) => n * 2);
 
console.log(doubled.join(', ')); // 2, 4, 6

The original numbers array does not change — map() always returns a new one.

filter — pick the matching ones

filter() keeps only the elements for which the function returned true. Such a checking function is called a condition, or a predicate:

const numbers = [5, 12, 8, 20];
 
const big = numbers.filter((n) => n > 10);
 
console.log(big.join(', ')); // 12, 20

If no element matches, the result is an empty array.

reduce — boil down to one value

reduce() walks through the array and accumulates a result. The function receives the accumulated value (often named sum or acc) and the current element, and the second argument of reduce() is the starting value:

const prices = [100, 250, 400];
 
const total = prices.reduce((sum, price) => sum + price, 0);
 
console.log(total); // 750

On the first step sum is 0, on the second 100, on the third 350, and the final result is 750.

An array of objects

Most often these methods work with arrays of objects. An object is a value in curly braces that stores data under names: product.title reads the title property. Objects are covered in detail in the next chapter.

const products = [
  { title: 'Tea', price: 5 },
  { title: 'Coffee', price: 12 },
];
 
const titles = products.map((product) => product.title);
 
console.log(titles.join(', ')); // Tea, Coffee

Chaining methods

map() and filter() return an array, so the next method can be called right after the previous one:

const orders = [
  { total: 500, paid: true },
  { total: 300, paid: false },
  { total: 200, paid: true },
];
 
const paidSum = orders
  .filter((order) => order.paid)
  .map((order) => order.total)
  .reduce((sum, total) => sum + total, 0);
 
console.log(paidSum); // 700

Read the chain from top to bottom: paid orders, their totals, the grand total.

Common mistake

If the body of an arrow function is wrapped in curly braces, the value must be returned with return. Without it the function returns undefined:

const numbers = [1, 2, 3];
 
const wrong = numbers.map((n) => { n * 2; });
const right = numbers.map((n) => { return n * 2; });
 
console.log(wrong[0]);         // undefined
console.log(right.join(', ')); // 2, 4, 6

In the short form without braces, (n) => n * 2, the return is implied.

Thanks for reading!

Donate to the site — we work hard for you.