본문 바로가기
Language/JavaScript (Modern)

[ES6+] 변수 let, const 그리고 var 에 대하여 (ft. scope, hoisting)

by 썸머워즈 2021. 12. 9.
반응형

자바스크립트의 변수 선언 방식 var ES6(ECMAScript6)에서 등장한 letconst에 대해 알아보자.

 

위에서 언급한 세가지의 변수 선언 방식의 차이점에 대해 알기위해서는

변수의 유효범위(scope) 와 호이스팅(hoisting)이라는 녀석들에 대해서도 같이 알아둘 필요가 있다.

 

그럼 변수선언부터 유효범위 그리고 호이스팅 이라는 녀석까지 하나하나 알아가보도록 하자.


1. 변수 선언 방법 (중복 선언, 재할당, 초기화 여부)

각 변수(var, let, const) 별로 중복 선언, 재할당, 초기화 여부에 대해 알아보자.

 

1-1) 중복 선언과 재할당

//////// 1. var ////////
var jsvar = 'mine';
var jsvar = 'it'; // 변수 중복선언 가능
jsvar = 'record'; // 변수 재할당 가능
console.log(jsvar); // record

//////// 2. let ////////
let jslet = 'mine';
let jslet = 'it';	
// 변수 중복선언 불가능
// Uncaught SyntaxError: Identifier 'jslet' has already been declared

let jslet = 'it';
jslet = 'record'; // 변수 재할당 가능
console.log(jslet); // record

//////// 3. const ////////
const jsconst = 'mine';
const jsconst = 'it';
// 변수 중복선언 불가능
// Uncaught SyntaxError: Identifier 'jsconst' has already been declared

const jsconst = 'it';
jsconst = 'record';
// 변수 재할당 불가능
// Uncaught TypeError: Assignment to constant variable

 

선예제 후설명을 하자면

var는 많이 써봤으니 알겠지만 아주 자유로운 녀석이라 중복선언, 재할당이 모두 가능하다.

let은 예제에서 보는것처럼 중복선언은 불가능하지만 재할당이 가능하여 값을 변경하여 사용이 가능하다.

const는 이름 그대로 constant(상수)를 의미한다고 생각하면 된다. 그래서 상수의 특징대로 var변수와 완전히 반대의 특성을 가져 중복선언, 재할당이 모두 불가능하며, 주로 전역변수에 상수를 선언해둘때 많이 사용된다.

 

1-2) 변수의 초기화

//////// 1. var ////////
var jsvar;
console.log(jsvar); // undefined

//////// 2. let ////////
let jslet;
console.log(jslet); // undefined

//////// 3. const ////////
const jsconst;
// 변수 선언과 동시에 반드시 값이 할당되어 있어야 한다.
// Uncaught SyntaxError: Missing initializer in const declaration

 

varlet변수의 초기화가 필요없이 선언만 해두는것이 가능하지만,

const반드시 값이 할당되어야 한다.

 

개인적이 생각이지만 이 차이는 아마 재할당이 가능하냐 불가능하냐의 여부에 따라 나뉜것으로 보인다.


2. 변수의 유효범위(scope)

유효범위라 하면 변수 혹은 데이터에 접근할 수 있는 범위라고 할 수 있다.

 

예제를 통해 접해보자.

 

1-1) var 변수의 유효범위(scope)

// 1. 함수사용
var jsvar = 7
console.log(jsvar); // result : 7

function jsFunc(){
  var jsvar = 10;
  console.log(jsvar); // result : 10
}
 
console.log(jsvar); // result : 7

// 2. 블럭사용
var jsvar = 7; 
console.log(jsvar); // result : 7
 
if (true) {
    var jsvar = 27;
    console.log(jsvar); // result : 27
}
 
console.log(jsvar); // result : 27

 

var 변수의 유효범위는 함수스코프(Function-scope)를 가진다.

이는 함수 외부에서는 참조할 수 없고 함수 내부에서 선언한 변수는 지역변수임을 의미하는데,

1번 예제를 보면 전역 변수와 지역 변수가 나뉘어 각각의 값을 가지고 있는 반면에

2번 예제는 if구문 안에 선언한 값이 전역변수의 데이터에 덮어씌워진것을 확인할 수 있다.

 

즉, if구문같이 그냥 블록(괄호)에 둘러 쌓여 있더라도 이는 전역변수로 사용됨을 의미한다.

var 변수는 함수단위에서만 지역변수로 사용이 가능한 것이다.

 

1-2) let과 const 변수의 유효범위(scope)

// 1. 함수사용
let jslet = 7
const jsconst = 7
console.log(jslet); // result : 7
console.log(jsconst); // result : 7

function jsFunc(){
  let jslet = 10
  const jsconst = 10
  console.log(jslet); // result : 10
  console.log(jsconst); // result : 10
}

console.log(jslet); // result : 7
console.log(jsconst); // result : 7

// 2. 블럭사용
let jslet = 7
const jsconst = 7
console.log(jslet); // result : 7
console.log(jsconst); // result : 7
 
if (true) {
  let jslet = 27
  const jsconst = 27
  console.log(jslet); // result : 27
  console.log(jsconst); // result : 27
}
 
console.log(jslet); // result : 7
console.log(jsconst); // result : 7

 

let const 변수의 유효범위는 블럭스코프(Block-scope)를 가진다.

이는 함수는 물론이고 if구문에서도 전역변수와 지역변수로 나뉘어져 서로 다른 변수를 의미한다.

 

즉, if구문같이 그냥 블럭(괄호)에만 둘러 쌓여 있어도 그냥 지역변수로 사용이 가능하다.


3. 호이스팅 (hoisting)

호이스팅이란 어떤 위치에 선언하든 위로 끌어올려지는 현상, 즉 변수가 선언과 할당으로 분리되는것을 의미한다.

일단 예제를 통해 쉽게 접해보자.

 

console.log(jsvar); // result : undefined
var jsvar = 'mine';

console.log(jslet); // Uncaught ReferenceError: jslet is not defined 
let jslet = 'it';

console.log(jsconst); // Uncaught ReferenceError: jsconst is not defined
const jsconst = 'record';

 

예제코드를 보면 하나같이 console.log()를 먼저 실행하고 변수를 나중에 선언하였다.

단순히 생각해보면 당연하게도 에러가 발생해야 옳다고 생각되는데, letconst에러가 발생하는 반면 var 변수는 에러는 커녕 undefined라는 결과를 출력해준다.

 

이게 호이스팅이 발생한 것인데, 호이스팅자바스크립트가 해당 변수의 선언을 영역의 최상위로 올려놓는것을 의미한다.

위 예제가 아래와 같은 경우로 발생한 것이다.

var jsvar;
console.log(jsvar); // result : undefined
jsvar = 'mine';

변수 뿐만 아니라 함수 역시도 호이스팅이 일어난다.

함수 중에서도 함수선언문은 호이스팅이 발생하고 함수표현식은 발생하지 않는다.

// 1.함수선언문
blog(); // result : mine-it-record
function blog() {
  console.log("mine-it-record");
}
 
// 2. 함수표현식
it();  // Uncaught TypeError: it is not a function
var it = function () {
  console.log("it");
}

여기까지 let, const 그리고 var 변수의 특징과 서로의 차이점에 대해 알아봤는데,

ES6의 가장 기본이되는 변수 선언에 대해 숙지하고 차근차근 ES6에 대해 알아가보자.

반응형


댓글

TOP