reduce() 메서드는 배열의 각 요소에 대해 주어진 리듀서(reducer) 함수를 실행하고,
하나의 결과값을 반환하는 메서드이다.
공부하기 전에 한 가지 알아두어야 할 것은, reduce
는 map
, filter
, sort
등을 모두 구현할 수 있는 근본있는 메서드라는 것이다.
리듀서 함수는 다음과 같이 4가지의 인자를 가진다.
acc
: 누적 값cur
: 현재 값reduce()
를 호출한 배열여기서 주로 쓰이는 인자는 accumulator
와 currentValue
이다.
이 2가지만 가지고도 우리는 많은 작업들을 reduce로 할 수 있어진다
[1,2,3,4,5]
와 같은 배열의 내부 합을 구한다고 해보자.
기존에는 다음과 같이 for문을 통해 sum을 구했었다.
const array = [1, 2, 3, 4];
let sum = 0;
for (let i = 0; i < array.length; i++) {
sum += array[i];
}
console.log(sum);
for문으로 각각의 배열 요소들을 sum에 더해주는데, reduce의 acc와 cur을 쓰면 이 과정이 훨씬 간편해진다.
[1,2,3,4,5].reduce((acc,cur)=>acc+cur);
// 15
[1,2,3,4]
와 같은 배열의 내부 요소에 2씩 곱해 [2,4,6,8]
과 같은 배열을 만들어보자.
이런 문제들은 map을 사용해 간단하고 직관적이게 해결했었다.
[1,2,3,4].map(num=>num*2);
이러한 map의 기능을 reduce를 통해서도 구현할 수 있다.
acc에 단순히 값을 더하는게 아닌, acc라는 배열에 cur값들을 push한다는 생각으로 접근할 수 있다.
const numbers = [1,2,3,4];
const MapNumbers = (acc,cur)=>{
acc.push(cur*2);
return acc;
}
const result = numbers.reduce(MapNumbers,[]);
console.log(result);
필터는 배열에서 원하는 요소들을 필터링 해주는 메서드이다.
사용법은 다음과 같다.
[1,2,3,4,5,6].filter(num=> num >= 4);
1부터 6까지 담겨있는 배열에서 4 이상의 값들을 필터링해줬다.
filter 조차도 reduce를 통해 구현 가능하다.
const numbers = [1,2,3,4,5,6];
const FilterNumber = (acc,cur)=>{
cur>=4 && acc.push(cur);
return acc;
}
const result = numbers.reduce(FilterNumber,[]);
console.log(result);
cumr>=4
가 참이면 &&
를 통해 acc.push(cur)를 하도록 만들어 주었다.
집의 전자제품의 제조사를 다음과 같이 배열에 저장했다고 치자.
['Samsung',LG','Samsung', 'Sony', 'Apple']
이제, 각 제조사별로 소유하고 있는 개수를 객체를 통해 구하려고 한다.
ex) {'Samsung': 2}
const Makers = ['Samsung','LG','Samsung', 'Sony', 'Apple'];
const sortMakers = (acc,cur)=>{
cur in acc ? acc[cur]++ : acc[cur]=1
return acc
}
const result = Makers.reduce(sortMakers,{})
console.log(result)
cur in acc
: acc
라는 객체 내부에 cur
이라는 키가 존재하면
acc[cur]++
: 값에 1을 더해준다.
만약, 키가 존재하지 않으면 acc[cur]=1
을 통해 키:값을 초기화 해준다.
여기까지 공부했다면 한가지 드는 의문점이 있다.
"아니 아까는 reduce가 과정을 줄여줘서 좋은거 아니였어? map, filter 등 메서드를 쓰는게 더 간편한데? "
라고 말이다.
reduce의 진짜 무기는 다양한 활용도에 있다.
reduce를 통해 단순한 연산부터 복잡한 함수형 프로그래밍까지 모두 다룰 수 있다.