회원 목록 중 한 명 찾기

1. 재사용 할수 있는 코드 && 없는 코드

데이터 리스트를 임의로 정의해보자

var users = [
    {id:1,name:"Hoon",age:27},
    {id:2,name:"woong",age:29},
    {id:3,name:"jimin",age:26},
    {id:4,name:"K",age:32},
    {id:5,name:"Tom",age:28},

    {id:6,name:"TT",age:32},
]

 

/** 재사용 할수 없는 코드 **/
var user;
for(var i =0,len=user.length;i<len;i++){
    if(users[i].id == 3){
        user = users[i];
        break;
    }
} 
console.log( user ); // {id:3,name:"jimin",age:26}



/** 재사용 할수 있는 코드 **/
function findById(list,id){
    for(var i=0,len=list.length;i<len;i++){
        if( list[i].id == id) return list[i]
    }
}
console.log( findById(users,3) );  //{id: 3, name: "jimin", age: 26}

 

위와 같은 코드는 재사용할 수 있지만, 회원 리스트에서 아이디 값뿐 아니라, 나이, 이름으로도 찾고 싶을 수도 있는데 이럴 때마다 함수를 생성/선언해야 하기 때문에 위 코드는 함수 형적이지 않다.

 

 

2. 함수형 코드 만들기

function findBy(list,key,val){
    for(var i=0,len=list.length;i<len;i++){
        if( list[i][key] === val ) return list[i]
    }
}
console.log( findBy(users,'name','Hoon') ) //{id: 1, name: "Hoon", age: 27}

 

인자 값 key에 객체의 key값과 찾고자 하는 value값으로 찾을 수 있게 된 함수이다. 

하지만, 더 많은 예외가 있을 경우 처리가 어렵다

  • key가 아닌 메서드를 통해 값을 얻어야 할 때
  • 두 가지 이상 조건이 필요할 때
  • ===이 아닌 다른 조건으로 찾고자 할 때

filter나 map처럼 인자로 키와 값 대신 함수를 사용하여 모든 상황에 대응 가능한 find함수를 만들어보자

function User(id,name,age){
    this.getId = function(){
       return id;
    }
    this.getName = function(){
       return name;
    }
    this.getAge = function(){
       return age;
    }
}
/* 새로운 데이터 리스트 생성 */
var users2 = [
    new User(1,'ID',32),
    new User(2,'AD',25),
    new User(3,'MJ',28),
    new User(4,'BJ',29),
    new User(5,'HA',24),
    new User(6,'HO',32),
]

/* 값대신 함수를 받아 처리 */
// 인자 predicate안에 함수식
// 인자 list 는 본문 맨위에 선언한 데이터
function find(list,predicate){
    for(var i=0,len=list.length;i<len;i++){
        if(predicate(list[i])) return list[i]
    }
}

console.log(
    find( users2, function(u){return u.getAge() == 25;} ).getName()
) // AD
console.log(
    find( users, function(u){return u.name.indexOf('j') != -1;} )
) // {id: 3, name: "jimin", age: 26}
console.log(
    find( users, function(u){return u.age == 32 && u.name == 'K'} )
) // {id: 4, name: "K", age: 32}
console.log(
    find( users2, function(u){return u.getAge() > 30} ).getName()
) // ID

 

 

3. 고차 함수 만들기

고차 함수란 함수를 인자로 받거나 함수를 리턴하는 함수
- 함수를 인자로 받아 필요한 때에 실행하거나 클로저를 만들어 리턴

find의 인자 predicate를 함수로 만들어서 인자 값 고차 함수 만들기

 

function bmatch1(key,val){
    return function(obj){
        return obj[key] === val;
    }
}
console.log( find(users, bmatch1('id',3) ) )        // {id: 3, name: "jimin", age: 26}
console.log( find(users, bmatch1('name','Hoon') ) ) // {id: 1, name: "Hoon", age: 27}
console.log( find(users, bmatch1('age',32) ) )      // {id: 4, name: "K", age: 32}

/**************************
*  여러 데이터 불러오기
*  전에 만들어뒀던 filter, map 활용 예):
***************************/
function filter(list, predicate){
    var new_list = [];
    for(var i=0,len=list.length; i<len; i++){
    	if(predicate(list[i])) new_list.push(list[i]);
    }
    return new_list;
}

function map(list, iteratee){
    var new_list = [];
    for(var i =0,len=list.length;i<len;i++){
        new_list.push(iteratee(list[i]));
    }
    return new_list;
}
console.log( filter(users, bmatch1('age',32) ) ) // 0: {id: 4, name: "K", age: 32}, 
                                                 // 1: {id: 6, name: "TT", age: 32}

 

 

4. 비교하는 함수 만들기

function object(key,val){
    var obj = {};
    obj[key] = val;
    return obj;
}

function match(obj,obj2){
    for(var key in obj2){
        if(obj[key] !== obj2[key]) return false;
    }
    return true;
}

function bmatch(obj2,val){
    if(arguments.length == 2) obj2 = object(obj2,val);
    return function(obj){
       return match(obj,obj2);
    }
}

console.log(
   match( find(users, bmatch('id',3)), find(users, bmatch('name','jimin')) )
) // true

console.log(
   find(users, function(u){return u.age == 32 && u.name == 'TT'}) 
) //{id: 6, name: "TT", age: 32}

 

 

 

>> [ 위 코드들 통합 ]

See the Pen qBqGNme by JNoony (@jnoony) on CodePen.

 

[출처::책] 함수형 자바스크립트
http://book.interpark.com/product/BookDisplay.do?_method=detail&sc.prdNo=272822398&gclid=EAIaIQobChMIi739ieqR7wIVOcEWBR2CgwMxEAQYASABEgLcrvD_BwE
728x90

+ Recent posts