2 분 소요


함수의 매개변수는 함수 몸체 내부에서만 참조할 수 있고, 함수 내부에서 선언한 변수는 함수 외부에서는 참조할 수 없고 함수 몸체 내에서만 참조할 수 있다.

왜냐하면 스코프가 정해져있기 때문이다


1. 스코프


모든 식별자(변수 이름, 함수 이름, 클래스 이름 등)는 자신이 선언된 위치에 의해 다른 코드가 식별자 자신을 참조할 수 있는 유효 범위가 결정된다

➞ 이를 스코프 라고 한다 (식별자가 유효한 범위)

// let, const는 중복 선언이 안되기 때문에 var를 사용
var x = 1;

fuinction func() {
  var x = 10;
  console.log(x)    // 10
}
console.log(x)    // 1


2. 스코프의 종류


스코프는 “전역스코프”, “지역스코프” 이렇게 두개로 나뉜다

구분 설명 스코프 변수
전역 코드의 가장 바깥 영역 전역 스코프 전역 변수
지역 함수 몸체 내부 지역 스코프 지역 변수

scope

출처 https://frontj.com/entry/5-Javascript%EC%9D%98-%EC%8A%A4%EC%BD%94%ED%94%84

위 그림을 보면 전역 스코프는 함수를 포함한 그 밖의 영역 제일 바깥쪽이다

그리고 지역 스코프는 foo()함수의 내부에 1개, bar()함수의 내부에 1개, 총 2개가 있다

  • 지역은 함수 몸체 내부를 뜻하고 지역변수는 자신의 지역 스코프와 하위의 지역 스코프에서도 유효하다
  • 전역 스코프는 어디에서나 유효하다(최상단에 있기 때문)


3. 스코프 체인

함수는 중첩될 수 있으므로(각각 함수 내부의 함수는 중첩함수, 외부는 외부함수) 스코프도 중첩된다

스코프가 함수의 중첩에 의해 계층적 구조를 가짐

지역 스코프의 상위 스코프는 함수기준 외부 함수의 스코프이다. 계층적으로 연결된 것을 스코프 체인이라고 한다


변수를 참조할때 자바스크립트 엔진은 스코프 체인을 통해 변수를 참조하는 코드의 스코프에서 시작하여 상위 스코프 방향으로 이동하며 선언된 변수를 검색한다

하위 스코프에서 유효한 변수를 상위스코프에서 참조할 수 없다

// let, const는 중복 선언이 안되기 때문에 var를 사용
var x = "global";

fuinction func() {
  var x = "inner";
  console.log(x)    // 내부
}
console.log(x)    // 외부

즉 내부에서 x를 호출했을 때 내부의 변수 x가 참조되지 외부의 x(global)이 참조될 수 없다는 뜻이다

렉시컬 환경
스코프 체인은 실행 컨텍스트의 렉시컬 환경을 단방향으로 연결한 것이다
변수 선언 -> 렉시컬환경에 키 등록
변수 할당 -> 해당하는 값 변경


4. 함수 레벨 스코프

var 키워드로 선언된 변수는 코드블럭이 아닌 함수에 의해서만 지역 스코프가 생성됨

const, let 키워드로 선언된 변수는 블록 레벨 스코프를 지원한다


5. 렉시컬 스코프

상위 스코프를 결정하는 패턴은 두가지가 있다

스코프 방법
동적 스코프 함수를 어디서 호출했는지에 따라 함수의 상위 스코프를 결정
렉시컬 스코프 함수를 어디서 정의했는지에 따라 함수의 상위 스코프를 결정

자바스크립트는 렉시컬 스코프를 따른다.

따라서 어디서 정의했는지에 따라 상위스코프를 결정

var x = "global";

function func1() {
  var x = "inner";
  funt2();
}

function func2() {
  console.log(x);
}

func1();   // global
func2();   // global

func2 함수가 외부에서 선언되었기 때문에 func1함수 내부에서 func2를 호출하더라도 “global”을 출력한다 (스코프가 전역이므로)



이웅모 선생님의 모던 자바스크립트 Deep Dive를 공부하기 위해 정리한 글입니다.
혹시나 보시다가 고칠 부분이나 마음에 안드시는 부분이 있다면 말씀해주시면 감사하겠습니다!