호이스팅이라는 개념과 TDZ라는 개념을 다시한번 정리하게 되었다.
호이스팅은 단순한게 선언된 변수가 최 상단으로 끌어올려지는 현상 !! 이라고 알고있었고 const, let을 쓰는이유는 var에서는 선언을 하면 호이스팅이 되어지는 문제점이 있어 es6 문법에서 새롭게 let과 const 라는 문법이 나오게 되었다는것을 알고 있었다 !
그런데 이번에 면접을 준비하면서 TDZ라는 개념을 접하게 되었고 내가 알고 있는것은 매우 기본만 알고있다는 것을 알게 되었다 ! 그렇다면 호이스팅과 TDZ는 무엇일까
호이스팅 - 선언된 변수가 최상단으로 끌어올려지는 현상
console.log('a') // undefined
console.log('b') // ReferenceError
var a = '호이스팅 test'
let b = '호이스팅 test'
이러한 경우를 살펴보면 var는 호이스팅이 되면 ‘호이스팅 test’ 값에 접근을 해야하는것인데 왜 undefined가 선언이 되는것이며 let으로 선언된 값은 왜 referenceError를 내는 것일까!!!
호이스팅의 경우 함수스코프 내에서 최상단으로 끌어올려지고, 그것이 아니라면 유효범위 ( 스코프 ) 최상단에 선언되는것을 의미한다. 여기서 중요한것은
호이스팅이란 선언된 변수의 값이 끌어올려지는 것이 아니라 ! 선언이 끌어올려지는것
여기서 생각해봐야할것은 선언, 초기화, 할당이라는 개념이다.
변수 생성단계는 크게 변수선언, 초기화 ,할당으로 나뉜다.
선언 단계이란 자바스크립트 엔진에 변수를 등록하여 존재를 알리는것이고,
초기화 단계란 그렇게 등록된 변수에 메모리를 확보하고 암묵적으로 undfined가 할당된다.
그리고 할당단계란 undefined로 초기화된 메모리에 값을 주는것을 의미한다.
var의 변수 생성단계
var는 선언과 동시에 초기화를 동시에 진행한다.
var는 선언과 동시에 초기화를 진행하기 때문에 undefined가 할당이 되어있다.
변수에 값을 할당한다.
var의 경우 변수의 선언과 동시에 초기화가 진행되기 때문에 undefined가 선언되어 호이스팅이 되었을때 undefined로 console이 찍히게 되는것이고 오류가 발생하지 않았다.
let과 const의 변수 생성단계
let, const는 var와 다르게 선언과 초기화 단계가 분리되어 있다. 그렇기 때문에 선언단계에서 실행컨텍스트에 변수를 등록했지만 초기화가 되기 전에 접근을 한것이기때문에 referenceError가 발생을 한것이다 ! 메모리가 확보되지 않았기 때문에 오류가 발생한것이다. 즉 호이스팅은 되지만 ! 접근이 불가한것이다 !!!!
let , const는 호이스팅이 안되는것이 아니라 호이스팅은 되지만 초기화 단계가 이루어지지 않았기때문에 오류가 발생하는것이다.
선언단계와 초기화 단계 사이에 접근이 불가한 것 그것이 바로 TDZ ( temporal Dead Zone) 의 상태이다.
const와 let의 경우 초기화 단계는 코드의 흐름의 순서대로 이루어지므로 const와 let이 초기화되기전에 선언이 먼저 일어났기때문에 접근이 불가한 것이다.
함수 선언식의 경우에도 선언, 초기화, 할당이 동시에 이루어지기 때문에 호이스팅이 일어나게 된다.
호이스팅 참조오류가 일어나는 경우 - const, let, 함수표현식, class 구문, 기본매개변수 (es6)
호이스팅도 되고 참조오류가 일어나지 않는 경우 - var, 함수선언식 , import