6월3일 목요일 til

김병훈·2021년 6월 3일
0

til

목록 보기
12/89

고차함수 이해하기

Achievement Goals

  • 일급 객체의 세 가지 특징을 알아야한다. (first-class citizen)
  • 고차함수에 대해서 알아야한다. (higher-order function)
  • 고차함수를 Javascript로 작성할 수 있어야한다.

1. 일급객체

특별한 대우를 받는 함수
Javascript에서 특별한 대우를 받는 일급 객체(first-class citizen)이 있다.
대표적인 일급객체 중 하나가 함수이다. Javascript에서 함수는 다음과 같이 특별하게 취급된다.

  • 변수에 할당할 수 있다. (assignment)
  • 다른 함수의 인자(argument)로 전달될 수 있다.
  • 다른 함수의 결과로서 리턴될 수 있다.

함수를 변수에 할당할 수 있기 때문에 함수를 배열의 요소나 객체의 속성값으로 저장할 수 있다. 이는 함수를 데이터(string, number, boolean, array, object)를 다루듯이 다룰 수 있다는 것을 의미한다.

첫번째. 변수에 함수를 할당하는 경우. square에 함수를 할당해주는 함수 표현식이다. js에서 함수는 일급객체이기 때문에 변수에 저장할 수 있다. 함수 표현식은 할당전에 사용할 수 없다.

 const square = function (num) {
return num * num;
};

// square에는 함수가 저장되어 있으므로 (일급객체) 
//함수 호출 연산자 ()를 사용할 수 있다. 
// output = square(7);
// console.log(output); // 49 

2.고차함수

고차함수는 함수를 인자로 받을 수 있고, 함수의 형태로 리턴할 수 있는 함수이다. 함수는 변수에 저장할 수 있다. 그리고 함수는, 함수를 담은 변수를 인자로 전달할 수 있다. 마찬가지로, 함수 내부에서 변수에 함수를 할당할 수있다. 그리고 함수는 이 변수를 리턴할 수 있다. 여기서 변수에 할당하지 않고 함수를 바로 이용할 수있다. 어떤 고차 함수에 인자로 전달하고, 고차함수는 함수자체를 리턴한다. 변수가 빠졌을 뿐, 동일하게 동작한다.

이때 어떤 작업이 완료 되었을 때 호출하는 경우가 많은 .. 즉 다른 함수(caller)의 인자로 전달되는 함수를 콜백 함수 (callback function)라고 한다.

콜백함수를 전달받은 고차함수는 , 함수 내부에서 이 콜백함수를 호출할 수 있다. caller는 조건에 따라 콜백함수의 실행여부를 결정할 수 있다. 호출하지 않거나, 여러번 실행하거나, 특정작업의 완료후에 호출하는 등..

함수를 리턴하는 함수, 함수를 인자로 받는함수 모두 고차함수로 사용한다.

1.다른함수를 인자로 받는 경우

function double(num) {
	return num * 2;
}

function doubleNum(func, num) {
	return func(num);
}

/* 함수 doubleNum은 다른 함수를 인자로 받는 고차함수이다.
 * 함수 doubleNum의 첫번째 인자 func에 함수가 들어올 경우 
 * 함수 func는 함수 doubleNum의 콜백함수이다.
 * 아래와 같은 경우, 함수 double은 함수 doubleNum의 콜백함수이다.
 */
 
 let output = doubleNum(double, 4)
 console.log(output); // 8 

2.함수를 리턴하는 경우

function adder(added) {
 	return function(num) {
         return num + added'
         };
}
/*함수 adder는 다른 함수를 리턴하는 고차함수이다. 
 *adder는 인자 한 개를 입력받아서 함수를 리턴한다.
 * 리턴되는 익명함수는 인자 한 개를 받아서 added와 더한 값을 리턴한다.
 */
 
 //adder(5)는 함수이므로 함수 호출연산자 ()를 사용할 수 있다.
 
 let output = adder(5)(3)
 console.log(output); // 8 
 
 //adder가 리턴하는 함수를 변수에 저장할 수 있다.
 // js에서 함수는 일급 객체이기 때문이다.
 
 const add3 = adder(3);
 output = add3(2);
 console.log(output); // 5 

3.함수를 인자로 받고 , 함수를 리턴하는 경우

function double(num) {
	return num * 2;
}

function doubleAdder(added, func) {
	const doubled = func(added);
   	return function (num) {
    	return num + doubled;
    };
}

// 함수 doubleAdder는 고차함수이다.
// 함수 doubleAdder의 인자 func는 함수 doubleAdder의 콜백함수이다.
// 함수 double은 함수 doubleAdder의 콜백으로 전달 되었다.

// doubleAdder(5, double)은 함수이므로, 함수 호출기호 ()를 사용할 수있다.
doubleAdder(5, double)(3); // 13 

// doubleAdder가 리턴하는 함수를 변수에 저장할 수있다. (일급객체)

const addTwice3 = doubleAdder(3, double);
addTwice3(2); // 8

내장 고차함수 이해하기

Achievement Goals

  • 배열 내장 고차함수 filter에 대해서 알아야한다.
  • filter에 대한 이해를 기반으로, 나머지 고차함수를 스스로 학습해야한다.
    • forEach, find, filter, map, reduce, sort, some, every
  • 추상화(abstraction) 에 대해 알아야한다.
  • 추상화 관점에서 고차함수가 갖는 이점에 대해 알아야한다.
  • 고차 함수를 활용하여 프로그램을 작성할 수 있어야한다.

자바스크립트에는 기본적으로 내장된 고차함수가 여럿 있다. 그중에서 배열 메소드들 중 일부가 대표적인 고차함수에 해당한다.

filter 메소드

배열의 filter메소드는 , 모든 배열의 요소중에서 특정 조건을 만족하는 요소를 걸러내는 메소드이다. 예를 들어 number 타입을 요소로 갖는 배열에서 짝수만을 걸러내거나, 18 보다 작은 수만을 걸러낸다. string 타입을 요소로 갖는 배열에서, 길이가 10이하인 문자열만 걸러내거나, 'korea'만 걸러낼 수 있다.

// 아래 코드에서 '짝수'와 '길이 5 이하' 는 문법오류 (syntax error) 에 해당한다.
// 의미만 이해해도 충분하다.
let arr = [1, 2, 3, 4];
let out put = arr.filter(짝수);
console.log(output); // ->> [2, 4]

arr = ['hello', 'code', 'states', 'happy', 'hacking'];
output = arr.filter(길이5이하)
console.log(output); // ->> ['hello', 'code', 'happy']

filter 메소드를 이용해 특정 조건을 만족하는 요소만 걸러낸다.

여기서 걸러내는 기준이 되는 특정 조건은 filter메소드의 인자로 전달된다. 이때 전달되는 조건은 함수의 형태이다. filter메소드는 걸러내기 위한 조건을 명시한 함수를 인자로 받기 때문에 고차함수이다. filter메소드가 동작하는 방식을 조금 더 자세히 살펴보면 다음과 같다.

// 아래 코드는 정확한 표현 방식은 아니다.
// 의미만 이해해도 충분하다.

let arr = [1, 2, 3];
// 배열의 filter메소드는 함수를 인자로 받는 고차함수이다.
// arr.filter를 실행하면 내부적으로 arr에 접근할 수 있다고 생각해도 된다.
arr.filter = function(arr, func) {
const newArr = [];
for (let i = 0; i < arr.length; i++) {
// filter에 인자로 전달된 콜백함수는 arr의 각 요소를 전달받아 호출된다.
// 콜백 함수가 true를 리턴하는 경우에만 새로운 배열에 추가된다.
if (func(arr[i]) === true) {
newArr.push(this[i]);
  }
 }
// 콜백 함수의 결과가 true인 요소들만 저장된 배열을 리턴한다.
return newArr;
};

/*
 * 보다 정확한 정의는 프로토 타입과 this를 학습한 후, 아래 코드를 통해 이해할 수 있다.
 * Array.prototype.filter = function(func) {
 *   const arr = this;
 *   const newArr = []
 *   for(let i = 0; i < arr.length; i++) {
 *     if (func(arr[i]) === true) {
 *       newArr.push(this[i])
 *     }
 *   }
 *   return newArr;
 * }
 */

filter메소드가 동작하는 방식

  • filter메소드는 배열의 요소를, 인자로 전달되는 콜백 함수에 다시 전달한다. 콜백 함수는 전달받은 배열의 요소를 받아 함수를 실행하고, 콜백 함수 내부 조건에 따라 true or false를 리턴해야한다. 적어도 filter메소드는 이런 함수를 기대하고 있다. 처음 본 코드에 이 점을 반영하여 다시 코드를 작성하면 , 다음과 같다.
// 함수 표현식
const isEven = function (num) {
	return num % 2 === 0;
};

let arr = [1, 2, 3, 4];
// let output = arr.filter(짝수);
// '짝수'를 판별하는 함수가 조건으로서 filter메소드의 인자로 전달된다.
let output = arr.filter(isEven);
console.log(output); // ->> [2, 4]

const isLteFive = function (str) {
// Lte = less then equal
	return str.length <= 5;
  };
  
  arr = ['hello', 'code', 'states', 'happy', 'hacking'];
  // output = arr.filter(길이 5이하)
  // ' 길이 5이하' 를 판별하는 함수가 조건으로서 filter 메소드의 인자로 전달된다.
  let output = arr.filter(isLteFive);
  console.log(output); // ->> ['hello', 'code', 'happy']

filter 메소드 사용 예시

profile
블록체인 개발자의 꿈을 위하여

0개의 댓글