Skip to main content

Array reduce() method

reduce() is one of the most powerful and versatile array methods in JavaScript: it folds an array step by step into a single value. That value can be a number, a string, an object, a new array or any other structure, which is why reduce() covers almost every data aggregation task.

Theory

TL;DR

  • reduce() walks the array from left to right and accumulates the result in an accumulator.
  • The callback has the signature (accumulator, currentValue, index, array) and must return the new accumulator.
  • The second argument, initialValue, sets the starting value and the type of the result.
  • Without initialValue the first element becomes the first accumulator, and an empty array throws a TypeError.
  • For a simple per element transformation prefer map(), for selection prefer filter(), and reach for reduce() when you need one summary value.

Quick example

javascript
const numbers = [1, 2, 3, 4]; const sum = numbers.reduce((acc, num) => acc + num, 0); console.log(sum); // 10

Step by step it works like this:

  1. acc = 0 (the initial value)
  2. 0 + 1 -> 1
  3. 1 + 2 -> 3
  4. 3 + 3 -> 6
  5. 6 + 4 -> 10

Syntax and parameters

javascript
const result = array.reduce((accumulator, currentValue, index, array) => { return newAccumulatorValue; }, initialValue);
ArgumentDescription
accumulatorthe accumulated value, that is whatever the previous iteration returned
currentValuethe current array element
indexthe index of the current element
arraythe array the method was called on
initialValuethe starting value of the accumulator, formally optional but strongly recommended

Typical use cases

Counting elements that satisfy a condition. reduce() is often used for aggregation: counts, statistics, merging.

javascript
const users = [ { name: 'Tim', age: 25 }, { name: 'Alex', age: 17 }, { name: 'John', age: 30 } ]; const adultsCount = users.reduce((acc, user) => { return user.age >= 18 ? acc + 1 : acc; }, 0); console.log(adultsCount); // 2

Turning an array into an object. Very handy when data has to be reshaped into another structure, for example a lookup dictionary.

javascript
const fruits = ['apple', 'banana', 'cherry']; const fruitMap = fruits.reduce((acc, fruit, index) => { acc[index] = fruit; return acc; }, {}); console.log(fruitMap); // { 0: 'apple', 1: 'banana', 2: 'cherry' }

Collapsing an array of objects into one number. The classic cart or report total.

javascript
const products = [ { price: 10 }, { price: 20 }, { price: 30 } ]; const total = products.reduce((acc, item) => acc + item.price, 0); console.log(total); // 60

The initial value and empty arrays

If initialValue is omitted, the first element becomes the accumulator on the first iteration and the walk starts from the second element.

javascript
const arr = [1, 2, 3]; const sum = arr.reduce((acc, num) => acc + num); console.log(sum); // 6

Here acc is 1 on the first iteration (the first element), and currentValue is 2, then 3.

If the array is empty and there is no initial value, the method throws:

javascript
[].reduce((acc, x) => acc + x); // TypeError: Reduce of empty array with no initial value

That is exactly why you should always pass an initial value, especially when the array comes from the network and may turn out to be empty.

When to use reduce() and when to use other methods

GoalIs reduce() a good fit
Sum or product of numbersYes
Counting or computing statisticsYes
Turning an array into an objectYes
Concatenating strings or arraysYes
Transforming every elementNo, use map()
Selecting elementsNo, use filter()

A comparison with the neighbouring iteration methods:

MethodWhat it doesWhat it returnsCan it break the loop
forEach()iterates over elementsundefinedno
map()transforms elementsa new arrayno
filter()selects elementsa new arrayno
find()finds the first matching elementthe element or undefinedyes
reduce()folds the whole array into one valueany type: number, string, objectyes, through logic in the callback

A formula worth memorising: arr.reduce((acc, elem) => newValue, initialValue).

Common mistakes

1. A missing return in the callback body. Curly braces cancel the arrow function's implicit return, so the accumulator becomes undefined.

javascript
arr.reduce((acc, num) => { acc + num }, 0); // undefined

The fix:

javascript
arr.reduce((acc, num) => { return acc + num }, 0);

2. A mismatched type for the initial value. If the elements are strings and the accumulator is a number, you get concatenation instead of addition.

javascript
['1', '2', '3'].reduce((acc, n) => acc + n, 0); // '0123', a string

The fix, with an explicit conversion:

javascript
['1', '2', '3'].reduce((acc, n) => acc + Number(n), 0); // 6

3. Mutating outside data. An object accumulator may be mutated because it was created inside the call, but mutating the source elements is a bad idea: it makes the result unpredictable.

4. Using reduce() where map() or filter() would do. Such code reads worse than a chain of simple methods and buys you nothing.

Short Answer

Interview ready
Premium

A concise answer to help you respond confidently on this topic during an interview.