[자바스크립트] 함수 선언문과 함수 표현식

박은정·2022년 2월 25일
0

자바스크립트

목록 보기
24/25
post-thumbnail

함수 선언문과 함수 표현식 모두 함수를 새롭게 정의할 때 사용됩니다.

함수 선언문 function declaration

함수 선언문은 function 정의부만 존재하고 별도의 할당 명령이 없는 것을 의미합니다. 따라서 반드시 함수명이 정의되어야 합니다.

function a() { }; // 함수명 a = 변수명
a(); // 실행OK

함수 표현식 function expression

함수 표현식은 정의한 function을 별도의 변수에 할당하는 것이기 때문에 함수명이 있어도 되고 없어도 됩니다. 따라서 함수명을 정의하지 않은 함수 표현식을 익명 함수 표현식이라고 하고 함수명을 정의한 함수 표현식을 기명 함수 표현식이라고 합니다.

일반적으로 함수 표현식은 익명 함수 표현식을 말합니다.

var b = function () { }; // 변수명 b = 함수명
b(); // 실행OK

var c = function d() { }; // 변수명 c, 함수명 d
c(); // 실행OK
d(); // 에러발생!!

기명 함수 표현식의 주의점

기명 함수 표현식을 쓸 이유가 없을 것 같다

외부에서는 함수명으로 함수를 호출할 수 없습니다. 함수명은 오직 함수 내부에서만 접근이 가능합니다.
과거의 기명 함수 표현식은 함수명이 잘 출력이 되지만 익명 함수 표현식은 undefined 또는 unnamed 값이 나왔기 때문에 기명 함수 표현식으로 디버깅을 하면서 어떤 함수인지 추적을 했습니다. 하지만 지금은 모든 브라우저에서 익명 함수 표현식의 변수명을 함수의 name 프로퍼티에 할당하기 때문에 이러한 문제는 발생하지 않습니다.

한편 c함수 내부에서는 c()로 호출하던 d()로 호출하던 잘 실행됩니다. 이렇게 함수 내부에서 재귀함수를 호출하는 용도로 함수명을 쓰면 됩니다. 다만 c()로 호출해도 되는데 굳이 d()로 호출하지 않을까 싶습니다.

함수 선언문과 함수 표현식의 차이

함수 선언문은 함수 전체를 호이스팅하는 반면, 함수표현식은 변수 선언문만 호이스팅됩니다.
여기서 함수 표현식에서 함수를 다른 변수에 값으로써 할당을 한 것이기 때문에 함수도 하나의 값으로 취급된다는 것을 알 수 있습니다.

// === 호이스팅 영역: 실제로 작동되지는 않지만 이해를 돕기 위해 코드로 적었습니다 ===
var sum = function sum (a,b) {
  return a + b;
}
 
var multiply;

// === 아래부터는 실제 코드입니다 ===
console.log(sum(1,2));
console.log(multiply(3,4));

var sum = function sum (a,b) {
  return a + b;
}
var multiply = function (a,b) {
  return a + b;
};

함수 선언문으로 선언된 sum함수는 함수 전체가 호이스팅되서 선언 전에 호출해도 아무 문제 없이 실행되기 때문에 혼란을 일으키는 원인이 될 수 있고, 함수 표현식에서 변수의 선언문만 호이스팅되고 변수의 할당부는 원래 자리에 남습니다.

함수 선언문의 혼란 예시

현업에서 개발자 A가 sum함수를 100번째 줄에서 선언했고 잘 썼습니다. 그러던 어느 날 서로 입사한 B가 같은 파일의 5000번째 줄에서 sum함수를 새로 선언하고 테스트를 거치지 않은 채 배포를 했습니다.

전역 컨택스트가 활성화될 때 전역 공간에 선언된 함수들이 모두 호이스팅되는데 이 때 동일한 변수명에 서로 다른 값을 할당한 경우, 나중에 할당한 값이 먼저 할당한 값을 덮어 씌우는 override가 발생합니다.
따라서 코드를 실행하는 중에 실제로 호출되는 함수는 오직 마지막에 할당한(=마지막에 선언된) 함수 뿐입니다.

이렇기 때문에 실제 로직 상에서는 많은 문제가 발생하고 있지만 sum함수에서는 아무런 에러를 발생하지 않습니다.

만약 이러한 sum함수를 함수 표현식으로 정의를 했다면 각자의 의도대로 잘 동작을 했을 것이고, sum함수를 처음 선언한 100번째 줄 이전에 sum함수를 호출하려 할 때 바로 에러가 발생하며 빠르게 디버깅을 할 수 있습니다.

따라서 상대적으로 함수 표현식이 더 안전합니다.

profile
새로운 것을 도전하고 노력한다

0개의 댓글