자바스크립트로 개발을 하다 보면 함수를 선언할 때 변수에 함수를 바로 할당 하는 경우와 function
예약어를 이용해 선언 할 때가 있다. 이 두경우의 차이점에 대해서 문득 궁금해졌고 어떤 차이가 있는지 알아보려고 한다.
JavaScript에서 함수를 사용할때 두가지 방식으로 사용할 수 있다.
function function1 () {
console.log("function1");
}
이처럼 function
예약어를 사용해서 사용하는 것을 함수 선언식 이라고 한다.
javascript 말고도 일반적인 프로그래밍 언어들에서 위 방식을 이용해 함수를 선언한다.
var function2 = function funcA () { // 함수의 이름을 정할수도
console.log("function2");
}
var function3 = function () { // 함수에 이름을 주지 않고 익명 함수로 쓸수도 있다.
console.log("function3");
}
이처럼 함수의 이름을 생략하고 바로 변수에 함수를 할당하는 방식을 함수 표현식 이라고 한다.
javaScript Docs의 함수 선언식, 표현식에 대한 글을 찾아보면 호이스팅에 대한 차이가 있다.
Function declaration hoisting (함수 선언 호이스팅)
Function declarations in JavaScript are hoisted to the top of the enclosing function or global scope. You can use the function before you declared it:
(자바스크립트에서 함수 선언은 그 선언을 둘러싼 함수의 최상부나 전역 범위(global scope)로 끌어올려집니다.)
hoisted(); // logs "foo"
function hoisted() {
console.log("foo");
}
함수 선언식으로 함수를 선언하게 되면 호이스팅이 발생해서 함수가 선언되기 전에 해당 함수를 사용할 수 있지만,
notHoisted(); // TypeError: notHoisted is not a function
var notHoisted = function () {
console.log("bar");
};
이처럼 함수 표현식으로 함수를 선언하게 되면 함수에 대한 호이스팅이 발생하지 않아 TypeError가 발생한다.
JavaScript에서 호이스팅이란, 변수의 선언과 초기화를 분리한 후 선언만 스코프의 최상단 으로 옮기는 것이기 때문이다.
notHoisted(); TypeError: notHoisted is not a function
var notHoisted = function () {
console.log("catfish");
};
// 선언부 : var notHoisted
// 변수의 초기화 : function () { console.log("catfish"); }
즉, 위 코드는 호이스팅 시 함수의 선언부인 var notHoisted
부분만 끌어올려지게 될 것이고.
var notHoisted = undefined;
// var로 선언한 변수는 호이스팅 시 undefined로 초기화된다.
// const나 let으로 선언한 변수의 경우 undefined로 초기화하지 않는다.
nonHoisted(); // TypeError: notHoisted is not a function
// 이 시점에서 nonHoisted는 undefined 값을 가지는 변수일 뿐이다.
notHoisted = function () {
console.log("catfish);
}
실제로는 이렇게 동작하게 된다. notHoisted
변수 자체는 사용할 수 있지만 해당 변수는 아직 함수가 할당되기 전이므로 함수를 할당하기 전까지는 해당 함수를 호출할 수 없게 된다.
호이스팅에 영향을 받지 않는다는 특징 이외에도, 함수 표현식은 클로져 사용 시나, 다른 함수의 인자로 함수를 전달할 때 유용하게 사용할 수 있다는 특징이 있다.
호이스팅에 영향을 받지 않기 때문에 선언하기 전에 함수를 호출할 수 없어서 코드의 가독성을 높일 수 있다.
function alertLog () { // 선언식의 경우 함수의 이름이 alertLog
alert("log");
}
---
// 변수명이 alertLog이고 함수명은 examLog가 된다.
var alertLog = function examLog () {
alert("log");
}
함수 표현식은 클로저를 구현할 때나, 함수의 인자로 전달할 때 유용하게 쓰일 수 있다.
function myFunc() { // 함수 선언식
var count = 0;
return function () { // 함수 표현식
console.log(count);
}
}
var element1 = document.getElementById("element1");
element1.onclick = function () { // 함수 표현식
console.log("element");
}
뭔가 비슷한거 같으면서 미묘하게 다른.. 이제 화살표 함수, 익명 함수, 명명 함수(?), 즉시 실행 함수 등 더 궁금한게 많아 졌다.
특히 화살표 함수와 일반 함수의 차이가 뭔지 전부터 궁금했다.
다음 포스트는 화살표 함수로 정했다!