let, const와 블록 레벨 스코프

ES6부터 let, const를 사용하게 되는데, var와는 여러가지 차이가 있다.

선언은 프로그래밍에서 필수기때문에 var와 let, const차이를 이해하고 넘어가지 않으면 많은 프로그래밍적 오류를 발생시킬수 있다.

 

 

변수 호이스팅 단계

  1. 선언단계(Declaration phase)

    • 변수를 실행시키는 실행 컨텍스트의 변수 객체에 등록, 이 객체는 스코프가 참조하는 대상이됨
  2. 초기화단계(Initialization phase)

    • 변수 객체에 등록된 변수를 위한 공간을 메모리에 확보 - 변수는 undefined로 초기화됨

  3. 할당 단계(Assignment phase)

    • undefined로 초기화 된 변수에 실제 값 할당

 

var

  • var 생략 시 전역변수로 선언

    • 의도하지 않게 선언된 전역변수는 변경이 일어날 확률이 높음

  • 변수 선언 이전에 참조 가능

    • 호이스팅 시 선언 단계에서 초기화 단계까지 한번에 이루어짐

  • 함수레벨 스코프

    • for문내에서 선언한 변수를 for외부에서 참조가능

 

사용이 편리한 var, 스코프가 넓어서 의도치 않은 변경이 생길 수 있고 복잡성이 증가될 수 있다.

때문에 변수의 스코프가 좁을수록 좋으며 불가피한 상황외에는 사용하지 않는것이 좋다.

 

 

let

  • const와 달리 재할당 가능

    • 명시적으로 객체 타입 변수의 주소값을 재할당 해야한다면 let을 사용한다  

  • 블록 레벨 스코프

    • 모든 코드 블록 내에서 코드가 유효, 블록 외부에서 참조할 수 없음

    • 전역 변수에서 사용하는 경우 전역객체의 프로퍼티가 아니다.

      • window.foo 같이 접근 불가

      • 보이지 않는 개념적인 블록내에서 존재

  • var는 같은 네이밍으로 중복 선언할 수 있었지만 let은 불가

  • 선언문 이전에 참조하면 참조에러

    • 스코프 시작부터 변수의 선언까지 일시적 사각지대(Temporal Dead Zone; TDZ)가 생기기때문이다.

    • 호이스팅 시 선언단계와 초기화 단계가 분리되어 진행

      • 선언단계 - 일시적 사각지대(TDZ) - 초기화단계 - 할당 단계

const

  • let과 달리 재할당 금지

    • 상수

    • 객체의 대한 참조를 변경하지 못하지만 객체의 프로퍼티는 보호되지않는다

      • 할당된 객체의 내용(프로퍼티 추가, 삭제, 변경)은 수정될 수 있다

      • 객체의 내용이 변경되더라도 객체 변수의 주소값이 변경되지 않는다.

      • 객체타입에는 const를 사용하는 것이 좋다

      • 만약 명시적으로 객체 타입 변수의 주소값을 재할당 해야한다면 let을 사용한다

  • 선언과 동시에 할당이 이루어져야한다

  • 블록 레벨 스코프(let 참고)

 

ES6 이상에서는 var 키워드를 사용하지 않는다.

let과 const를 사용하며 원시 값(상수)이나 객체에는 가급적 const를 사용한다.

let을 사용할때는 스코프를 최대한 좁게 만든다.

객체의 재할당이 확정되지 않았을 경우 const로 먼저 선언하고 추후 let으로 변경하자

 


참고

let, const와 블록 레벨 스코프

 

참고에 자료로 명시되어있는 사이트

ECMAScript 6

ECMAScript 6 New Features: Overview & Comparison

ES6 compat table

Temporal dead zone and errors with let

Are variables declared with let or const not hoisted in ES6?

 

+ Recent posts