스코프 체인

October 02, 2022

스코프란 무엇일까요? MDN은 다음과 같이 설명합니다.

현재 실행되는 컨텍스트를 말한다. 여기서 컨텍스트는 값과 표현식이 “표현”되거나 참조 될 수 있음을 의미한다. 만약 변수 또는 다른 표현식이 “해당 스코프”내에 있지 않다면 사용할 수 없다. 스코프는 또한 계층적인 구조를 가지기 때문에 하위 스코프는 상위 스코프에 접근할 수 있지만 반대는 불가하다.

쉽게 말하자면 스코프는 변수에 접근할 수 있는 프로그램 상의 범위입니다. 자바스크립트 엔진은 스코프를 보고 변수의 접근 가능성을 결정합니다. 자바스크립트에는 3가지 종류의 스코프가 있습니다.

전역 스코프

전역 스코프는 전역 네임스페이스에 선언된 변수 또는 함수가 가지는 스코프입니다.

지역/함수 스코프

함수 또는 메소드 내에 선언된 변수 또는 함수가 가지는 스코프입니다. ES6 이전에 자바스크립트에서 변수를 선언하는 방법은 한가지, 바로 var 키워드를 사용하는 것이었습니다. var를 사용하여 변수를 선언하는 자바스크립트는 다른 대부분의 프로그래밍 언어와 다른 동작 형태를 보입니다. 바로 변수가 함수 스코프를 가진다는 것이죠.

변수가 함수 스코프를 가지면:

  1. 함수 밖에서는 접근할 수 없습니다.
  2. 함수 외의 블록은 스코프로 취급되지 않습니다. 즉, 조건문과 반복문 등의 블록에서도 같은 함수 내에 있다면 접근 가능합니다.
if (true) {
  var name = "Woody"
}

console.log(name) // 'Woody'

블록 스코프

ES6에서 추가된 letconstvar와는 달리 블록 스코프를 갖습니다. 블록 스코프에서는 어떤 블록이라도 스코프가 됩니다. 함수, 조건문, 반복문 등 모든 블록이 스코프로 취급됩니다.

if (true) {
  var name = "Woody"
}

console.log(name) // 'undefined'

여러분은 이제 자바스크립트에서 스코프가 어떤 의미를 갖는지 알게 되었습니다! 그렇다면 스코프 체인이란 무엇일까요?

스코프 체인

다시 한번 MDN의 스코프 문서를 읽어보면:

스코프는 또한 계층적인 구조를 가지기 때문에 하위 스코프는 상위 스코프에 접근할 수 있지만 반대는 불가하다.

이것이 스코프 체인입니다. 스코프 체인은 자바스크립트 코드에서 스코프가 어떻게 연결되어 있는지 정의합니다. 다음의 코드를 봅시다.

var x = "전역 x"
var z = "전역 z"

function 외부() {
  var y = "외부 y"
  console.log(x) // '전역 x'
  console.log(y) // '외부 y'

  function 내부() {
    var x = "내부 x"
    console.log(x) // '내부 x'
    console.log(y) // '외부 y'
    console.log(z) // '전역 z'
  }

  내부()
}

외부()

console.log(x) // '전역 x'
console.log(y) // 'Uncaught ReferenceError: y is not defined'

함수 내부에 함수가 중첩되어 있어 상당히 복잡해 보이네요. 자바스크립트 엔진은 복잡한 스코프 사이에서 스코프 체인을 탐색하며 변수의 값을 평가합니다.

내부 함수에서 x, y, z의 값을 알기 위해서 자바스크립트 엔진은:

  1. 내부 함수 스코프에서 x, y, z의 값을 찾습니다. => x = "내부 x"
  2. 외부 함수 스코프에서 y, z의 값을 찾습니다. => y = "외부 y"
  3. 전역 스코프에서 z의 값을 찾습니다. => z = "전역 z"

이처럼 변수는 존재하는 가장 가까운 상위 스코프의 값으로 평가됩니다. 만약 전역 스코프에서도 변수를 찾지 못하면 ReferenceError를 throw합니다.

참고


우정민

웹 개발, 프론트엔드