스코프(Scope)
모든 식별자(변수 이름, 함수 이름, 클래스 이름 등)는 자신이 선언된 위치에 의해 다른 코드가 식별자 자신을 참조할 수 있는 유효 범위가 결정된다. 이를 스코프라 한다. 즉, 스코프는 식별자가 유효한 범위를 말합니다.
💡식별자 결정
변수 이름, 함수 이름, 클래스 이름과 같은 식별자가 본인이 선언된 위치에 따라 다른 코드에서 자신이 참조될 수 있을지 없을지 결정되는 것
자바스크립트 스코프의 특징
대부분의 언어는 블록 레벨 스코프를 따르지만, 자바스크립트는 함수 레벨 스코프(function-level scope)를 따릅니다.
함수 레벨 스코프란 함수 코드 블록 내에 선언된 변수는 함수 코드 블록 내에서만 유효하고 함수 외부에서는 유호히지 않다(참조할 수 없다)는 것입니다. 단, ECMAScript 6에서 도입된 let, const keyword를 사용하면 블록 레벨 스코프를 사용할 수 있습니다.
var var1 = 1;if (true) {var var2 = 2;if (true) {var var3 = 3;}}function foo() {var var4 = 4;function bar() {var var5 = 5;}}console.log(var1);console.log(var2);console.log(var3);console.log(var4);console.log(var5);// output// 1// 2// 3// var4 is not defined// var5 is not defined
var a = 3;var b = 5;var bar = function () {var b = 7;var c = 11;console.log(a, b, c);a += b + c;console.log(a, b, c);};console.log(a, b);bar();console.log(a, b);// output// 3, 5// 3 7 11// 21 7 11// 21 5
스코프의 종류
변수는 자신이 선언된 위치에 의해 자신이 유효한 범위인 스코프가 결정됩니다.
전역 스코프(Global scope)
- 코드 어디에서든지 참조할 수 있습니다.
지역 스코프 (Local scope or Function-level scope)
- 함수 코드 블록이 만든 스코프로 함수 자신과 하위 함수에서만 참조할 수 있습니다.
스코프 체인
스코프가 계층적으로 연결된 것을 스코프 체인이라고 합니다.
모든 지역 스코프의 최상위 스코프는 전역 스코프입니다. 상위 스코프에서 유효한 변수는 하위 스코프에서 자유롭게 참조할 수 있지만 하위 스코프에서 유효한 변수를 상위 스코프에서 참조할 수 없습니다.
블록 레벨 스코프
C나 자바 등을 비롯한 대부분의 프로그래밍 언어는 함수 몸체만이 아니라 모든 코드 블록(if, for, while, try/catch)이 지역 스코프를 만듭니다. 이러한 특성을 블록 레벨 스코프라 합니다.
함수 레벨 스코프
var 키워드로 선언된 변수는 오로지 함수의 코드 블록(함수 몸체)만을 지역 스코프로 인정합니다.
var x = 1;if (true) {var x = 10;}console.log(x); // 10
var i = 10;for (var i = 0; i < 5; i++) {console.log(i);}console.log(i); // 5
렉시컬 스코프, 정적 스코프
- 함수를
어디서 정의했는지에 따라 상위 스코프를 결정합니다. - Javascript 및 대부분의 프로그래밍 언어에서 사용하는 방법입니다.
var x = 1;function foo() {var x = 10;bar();}function bar() {console.log(x);}foo(); // ?bar(); // ?// output// 1// 1
위 예제는 전역 변수의 x의 값 1 을 두번 출력합니다. 그 이유는 foo와 bar의 상위 스코프는 전역 스코프이기 때문입니다.