호이스팅(Hoisting)이란?
호이스팅의 사전적 정의는 "끌어올리기"이다. 호이스팅은 Javascript에서 변수와 함수 선언이 해당 스코프의 최상단으로 끌어올려지는 현상을 의미한다. 하지만 실제로 끌어올려지는 것은 아니다. 브라우저의 Javascript 엔진이 코드를 해석할 때, 위에서 아래로 순차적으로 실행한다. 그리고 호이스팅이 발생하는 변수나 함수는 해당 스코프의 맨 위 상단으로 끌어올려져 변수가 선언되기 전에 사용할 수 있다. 또한, 모든 함수와 변수들은 렉시컬 환경(Lexical Environment) 내에 메모리에 추가된다.
모든 선언은 호이스팅되지만 var는 undefined로 초기화되는 것과 달리 let, const는 초기화되지 않은 Temporal Dead Zone 상태로 유지된다. TDZ는 일시적 사각지대라는 의미로, 스코프 시작부터 초기화 시작 사이의 구간을 의미한다. 이 구간에서 선언되지 않거나 초기화 전인 변수를 참조하게 되면 에러가 발생한다.
변수 호이스팅(Variable Hoisting)
console.log(a); // undefined
var a = "A"
var = a;
console.log(a); // undefined
a = "A";
아래 코드는 변수를 호이스팅한 상태의 코드이다. 변수 a를 호이스팅 했기 때문에 에러가 나지않고 undefined로 출력된다. var는 선언과 동시에 undefined가 할당되기 때문이다.
그러나 let, const는 선언만 될 뿐, 초기화가 이루어지지 않은 TDZ에 들어가게 된다. let, const는 초기화되지 않은 상태로 유지된다!
console.log(b); // ReferenceError...
let b = "B";
위와 같이 b는 호이스팅이 되지만 초기화가 이루어지지 않은 상태이므로 ReferenceError가 발생한다.
함수 호이스팅(Function Hoisting)
함수 호이스팅에서 중요한 점은 함수 선언식은 호이스팅 되지만, 함수 표현식은 호이스팅되지 않는다는 것이다.
func(); // "hello"
function func() {
console.log("hello")
}
함수 선언식으로 작성한 함수는 해당 스코프의 최상단으로 끌어올려진다. 험수를 선언하기 전에 호출해도 오류가 발생하지 않는다. 함수를 선언하는 시점에 메모리 공간이 할당되기 때문이다.
func(); // TypeError: func is not a function...
var func = function() {
console.log("bye")
}
함수 표현식은 호이스팅되지 않는다. 그래서 함수 표현식을 작성한 이후 부터 아래에서 함수를 사용할 수 있다.
호이스팅은 함수나 변수를 어디에 작성하였는지 상관없이 사용하기 위해서 만들어진 기능이다. 그러나 이러한 특성으로 인해 생각지도 못한 곳에서 버그를 일으킬 수 있다. 호이스팅을 이해하고 활용할 때, 변수와 함수를 선언하는 위치와 스코프를 잘 고려하여 개발하는 것이 중요하다. 호이스팅을 의도적으로 사용하는 경우가 아니라면 let, const, 함수표현식을 사용하는 것이 좋다.
'TIL' 카테고리의 다른 글
[JS] 프로토타입(prototype) (0) | 2023.07.20 |
---|---|
[JS] 클로저(Closure) (0) | 2023.07.18 |
[JS] 실행컨텍스트 (0) | 2023.07.14 |
[JS] 화살표함수(Arrow Function)와 this (0) | 2023.07.10 |
[JS] let | var | const (0) | 2023.07.09 |