12.1~2 함수란, 함수 사용 이유

함수는 일련의 과정을 문으로 구현하고 코드블록으로 감싸서 하나의 실행 단위로 정의한 것이다.

함수 내부로 입력을 전달받는 변수를 매개변수(parameter), 입력을 인수(argument), 출력을 반환값(return value)이라고 한다.

함수는 함수 정의(function definition)롤 통해 생성하고 함수 호출(function call/invoke)을 통해 실행한다.

자주 사용하는 코드를 함수로 정의해두면 같은 코드를 여러군데서 반복하지 않고 함수 이름으로 호출만 하면 되기 때문에 재사용성이 높아지고 실수할 확률이 줄어들어 코드의 신뢰성을 높여준다. 또 함수의 내부적 기능을 수정해야 할 때 함수가 정의된 부분에서 한번만 바꿔주면 해당 함수를 호출하는 모든 곳에서 수정된 기능을 사용할 수 있어서 유지보수가 편해진다.

12.3 함수 리터럴

자바스크립트에서 함수는 객체이기 때문에 함수 리터럴로 생성할 수 있다. 함수 리터럴은 함수 이름, 매개변수 목록, 함수 몸체로 구성된다.

const checkFresh = function leftover(food){
  let freshness = false;
  if(food.buy < 3) freshness = true;
  return freshness;
}

위에서는 함수 리터럴을 변수에 할당하고 있다. 리터럴은 값을 생성하기 위한 표기방식이다. 함수 리터럴도 평가되어 값을 생성하는데 이 값은 객체다. 즉 함수는 객체다.

12.4 함수 정의

  1. 함수 선언문
function add(x, y){
  return x + y;
}

함수 선언문은 함수 리터럴과 형태는 같지만 함수 이름을 생략할 수 없다. 함수 선언문은 표현식이 아니라 문이다.

//
// 내용 추가 필요
//

  1. 함수 표현식

자바스크립트 함수 같이 값의 성질을 갖는 객체를 일급 객체라고 한다. 일급 객체는 함수를 값처럼 자유롭게 사용할 수 있다는 뜻이다.

함수 표현식은 함수 리터럴로 생성한 함수 객체를 변수에 할당해서 정의하는 방식이다. 이때 함수 리터럴의 함수 이름은 생략할 수 있다. 이런 함수를 익명 함수라고 한다.

const add = function(x, y){
  return x + y;
}

함수 표현식에서 함수 이름은 몸체 내부에서만 유효한 식별자이기 때문에 함수 이름으로 함수를 호출할 수 없다.

const add = function foo(x, y){
  return x + y;
}

add(1, 2);	// 3
foo(1, 2);	// ReferenceError: foo is not defined
  1. 함수 생성 시점과 함수 호이스팅

함수 선언문으로 정의한 함수와 함수 표현식으로 정의한 함수는 생성시점이 다르다.

함수 선언문은 런타임 전에 함수 객체가 먼저 생성돼서 코드의 선우로 끌어 올려진 것처럼 동작한다. 이것을 함수 호이스팅(function hoisting)이라고 한다.

함수 표현식으로 정의한 함수는 변수에 함수 객체를 할당하는 것이기 때문에 런타임에 변수에 할당된 함수 리터럴이 평가돼서 함수 객체가 된다. 따라서 함수 호이스팅이 아니라 변수 호이스팅이 발생한다.

add(1, 2);	// 3
sub(1, 2);	// TypeError: sub is not a function

// 함수 선언문 -> 함수 호이스팅 발생
function add(x, y){
  return x + y;
}

// 함수 표현식 -> 변수 호이스팅 발생
var sub = function(x, y){
  return x - y;
}

함수 선언문으로 정의한 add는 함수 호이스팅으로 런타임 전에 함수 객체가 생성되어 있다. 따라서 첫번째 줄에서 바로 add 함수를 호출해도 에러 없이 실행된다.

var 키워드로 선언된 변수 sub는 변수 호이스팅으로 런타임 전에 undefined로 초기화된다. 따라서 두번째 줄에서 sub(1, 2);를 실행하려고 하면 undefined를 호출하려는 것이기 때문에 TypeError가 발생한다.

  1. Function 생성자 함수

자바스트립트 빌트인 함수인 Function 생성자 함수에 매개변수 목록과 함수 몸테를 문자열로 전달해서 new 연산자와 함께 함수 객체를 생성할 수 있다.

var add = new Function('x', 'y', 'return x + y');

하지만 Funtion 생성자 함수로 함수를 생성하는 방식은 일반적이지 않고 바람직하지도 않다.

  1. 화살표 함수

ES6에서 도입된 화살표 함수(arrow function)는 화살표 => 를 이용해서 함수를 선언하고 항상 익명함수로 정의한다.

const add = (x, y) => x + y;

화살표 함수는 기존 함수보다 표현뿐만 아니라 내부 동작도 간략화되어 있다. (자세한 내용은 생성자함수, this, 프로토타입, arguments 객체를 먼저 보고 26.3절 참고)

12.5 함수 호출

12.6 참조에 의한 전달과 외부 상태의 변경

12.7 다양한 함수의 형태


이웅모 저자의 <모던 자바스크립트 Deep Dive> 책으로 스터디 하면서 공부한 내용들을 요약 정리해서 올리는 글입니다. 더 자세한 내용이 궁금하신 분들은 책을 봐주세요.

0개의 댓글