함수형 반복
- 12.1 함수형 도구 — map, filter, reduce
- 12.2 map() 도출하기
- 12.3 filter() 도출하기
- 12.4 reduce() 도출하기
- 12.5 세 도구의 관계
map, filter, reduce는 단순히 for 루프를 줄여주는 편의 함수가 아니야 — 의도를 명확하게 표현하는 도구야.
10~11장에서 일급 함수와 고차 함수를 배웠으니, 이제 가장 유명한 함수형 도구들을 직접 만들어볼 차례야. 이미 알고 있는 사람도 많겠지만, 이 챕터의 포인트는 "왜 이런 함수가 필요한가"를 for 루프에서 도출하는 과정에 있거든. MegaMart에서 모든 고객의 이메일 목록을 뽑아줘 하면 map, VIP 고객만 골라줘 하면 filter, 전체 주문 금액 합계를 구해줘 하면 reduce야. for 루프 대신 이걸 쓰면 무엇을 하고 싶은지가 코드에 바로 드러나.
먼저 비슷한 for 루프 두 개가 있다고 해봐 — 하나는 .email을 뽑고, 하나는 .name을 뽑아. 10장에서 배운 대로 달라지는 부분을 콜백으로 빼면:
function map(array, f) {
var result = [];
for (var i = 0; i < array.length; i++) {
result.push(f(array[i]));
}
return result;
}
var emails = map(customers, function(c) { return c.email; });
var names = map(customers, function(c) { return c.name; });
**map()**은 배열의 모든 원소에 함수를 적용해서 새 배열을 만드는 거야. 입력 배열과 출력 배열의 길이가 같고, 각 원소가 독립적으로 변환되고, 원본 배열은 변경되지 않아.
같은 방식으로 조건 부분을 콜백으로 빼면 filter가 나와:
function filter(array, f) {
var result = [];
for (var i = 0; i < array.length; i++) {
if (f(array[i]))
result.push(array[i]);
}
return result;
}
var vips = filter(customers, function(c) {
return c.totalSpent > 1000;
});
**filter()**는 배열에서 조건을 만족하는 원소만 골라서 새 배열을 만들어. 출력 배열의 길이는 입력 이하이고, 원소 자체는 변경되지 않아.
누적 로직을 콜백으로 빼면 reduce가 나오고:
function reduce(array, init, f) {
var accum = init;
for (var i = 0; i < array.length; i++) {
accum = f(accum, array[i]);
}
return accum;
}
var total = reduce(customers, 0, function(total, c) {
return total + c.totalSpent;
});
**reduce()**는 배열의 원소를 하나씩 누적기(accumulator)에 결합해서 하나의 값으로 만들어. 숫자, 문자열, 객체, 배열 등 뭐든 가능하고, **초기값(init)**이 필요하지. 사실 reduce()가 가장 강력해 — map()과 filter()를 reduce()로 구현할 수 있거든.
세 함수를 정리하면 map은 모든 원소 변환(배열 → 같은 길이 배열), filter는 조건에 맞는 원소 선택(배열 → 같거나 짧은 배열), reduce는 원소를 하나로 합침(배열 → 단일 값)이야. 이 세 가지만 알면 대부분의 배열 처리 로직을 for 루프 없이 표현할 수 있어. map(customers, getEmail)을 보면 "모든 고객의 이메일을 뽑는구나"가 바로 읽히지만, for 루프 버전은 코드를 한 줄씩 따라가야 뭘 하는지 알 수 있잖아.
정리
12장 읽고 기억할 거 세 가지:
- map = 모든 원소 변환, filter = 조건 선택, reduce = 하나로 합치기. for 루프의 세 가지 패턴을 추상화한 것
- reduce가 가장 강력. map과 filter를 reduce로 구현 가능
- 이 도구들의 진짜 가치는 의도 표현. "무엇을 하고 싶은가"가 코드에 바로 드러난다