Iterable Protocol을 따르는 값들은, Map,Filter,Reduce와 함께 쓰면 아주 실용적으로 쓸 수 있게 됩니다.
(순회를 간단하고, 직관적으로 할 수 있고, 필요한 값들을 뽑아 낼 수 있습니다)
Map
Map은 JSON과 같은 "데이터 파일"이 입력이 들어올 때,하나의 함수로 내가 원하는 값을 뽑아낼 수 있도록,하는 장점이 있습니다. 예시를 보면서, Map에 대한 느낌을 받아보시죠!
- 아래와 같은 학생정보가 있다고 합시다
const students=[
{name:"Kim",major:"ComputerScience"},
{name:"Lee",major:"Business"},
{name:"Jay",major:"Music"},
{name:"Dode",major:"Rap"},
{name:"Yoon",major:"Cooking"},
]
- 위의 학생 정보에서, 우리가 Map을 모르는 상태에서, name과 major의 정보를 알고싶다면, 아래와 같은 코드를 떠올릴 수 있겠습니다.
const students=[
{name:"Kim",major:"ComputerScience"},
{name:"Lee",major:"Business"},
{name:"Jay",major:"Music"},
{name:"Dode",major:"Rap"},
{name:"Yoon",major:"Cooking"},
]
//for of문을 사용해보기
let names=[];
for (const n of students){
names.push(n.name);
}
//내가 전공을 알고싶다면?
let majors=[]
for (const n of students){
majors.push(n.major);
}
위의 코드를, map을 이용하면서, "함수형"답게 짜보겠습니다.
- 함수형에서는 순수함수를 지향하고 있습니다. 따라서, 인자값(Parameter)을 처리해서, return값을 줍니다.
- map에서 iter(이터러블)을 받게되면, 이터러블 안에 속성(이름,전공과 같은)이 어떤것이 있는지 모르기 때문에, 어떤 속성이 있는지 받아줄 function이 필요하게 됩니다.
- 이 속성은, 사용자가 정의해야 하기 때문에, function으로 Parameter을 받게됩니다.
//map(탐색할것,탐색할 자료)
const map = (f,iter) =>{
res=[]
for (const a of iter){
res.push(f(a))
}
return res
}
//내가 만약, name을 알고싶다면?
console.log(map(s=>s.name,students));
//내가 만약, major을 알고싶다면?
console.log(map(a=>a.major,students));
위와 같이, map은 iterable이면, 동작할 수 있도록 만들어놓으면
- Generator로 생성한 모든 값들을 순회할 수 있게 되고,
- 결국, 거의 모든 값들을 순회할 수 있게 만들어지게 됩니다.
응용!
저번에 만들어놓은 짝수Iterable을 통해서, N까지 짝수를 나열하는 코드를 짜보겠습니다!
See the Pen JS_Example_Map by Doge (@DogeIsFree) on CodePen.
활용
Map은 JS에서 Array,String,Map 등, Iterator로 구현되어 있는 자료형에서 사용할 수 있는 메소드이고, 동작원리는 위에서 예제들을 짜면서 ,충분히 이해가 됬을거다!
다른점이라면, array안에서는 메서드 형태로 구현이 되어있기 때문에, this도 쓰였을거고, 외부 배열을 받는 형태로 구현이 되어있지 않을거라는 점이다!
OneToFive=[1,2,3,4,5]
/*
Map Format
arr.map(callback(currentValue[, index[, array]])[, thisArg])
*/
total=OneToFive.map((value)=>{
return value+1;
})//20
res=total.map((value)=>{
if (value%2===0){
return "짝수";
}
else{
return "홀수";
}
})
Filter
원하는 값을 조건에 맞게, Filtering하고 싶다면, 어떻게 해야할까?
우리가 쇼핑을 한다고 했을 때
- 자본의 사정에 따라서 2만원 이하의 상품만 보고싶거나
- 품질을 생각해서, 난 2만원 이상의 상품만 보고싶다고 생각할 수 있을것이다.
아래와 같은 상품목록이 있다고하자.
const products = [
{name:"반팔티",price:15000},
{name:"긴팔티",price:20000},
{name:"후드티",price:30000},
{name:"바지",price:25000},
{name:"반바지",price:20000},
]
Map에서 했던것 처럼, 바로 함수형으로 구현하면 아래와 같이 될 것이다 :)
const filter = (f,iter) =>{
let res=[];
for (const a of iter){
if (f(a)) res.push(a);
}
return res;
}
console.log(...filter(p=>p.price>=20000,products));
활용
JS에서 Filter 또한 구현되어 있다.
/*
arr.filter(callback(element[, index[, array]])[, thisArg])
*/
const words=["hello","limit","title","aa","bb","cc"]
const res=words.filter(word=>word.length<3);
console.log(res);
//[aa,bb,cc]
Ref
이 글은 유인동님의 함수형 프로그래밍과 JS ES6강의를 보고 나름대로 정리해서, 작성한 글 입니다. :)
https://www.inflearn.com/course/functional-es6/dashboard
'Web Front-end > 함수형 프로그래밍(FP)' 카테고리의 다른 글
[JS/함수형] Go, Pipe (0) | 2022.05.27 |
---|---|
[JS/함수형] Reduce (0) | 2022.05.25 |
[JS/함수형] 제너레이터와 이터레이터 (0) | 2022.05.22 |
[JS/함수형] Iterable Custom/전개연산자 (0) | 2022.05.18 |
[JS/함수형] for..of 달라진 순회방법 (0) | 2022.05.18 |