개요
- 자바스크립트에서는 렉시컬 스코프(Lexcial Scope) 라는 스코핑 방식을 이용한다.
- 이는 굉장히 낯설은 영단어로 처음 스코프 개념을 접하는 프로그래밍 초보자들에게 많은 혼란을 준다.
Lexical Scope 란?
- Lexical Scope 란 한글로 번역하면 어휘적 스코프이다.
- 어휘적 스코프라는 말을 들었을 때 이 스코핑 방식에 대해 이해한다면, 당신은 프로그래밍 고인물일 확률이 높다.
- Lexical Scope 는 Static Scope (정적 스코프) 라고도 불리운다.
- 정적 스코프라고 불리우는 이유는 스코프가 컴파일 타임에 결정되고 변하지 않기 때문이다.
- 런타임에 스코핑을 지원하는 Dynamic Scope 와 다른 방식의 스코프이다.
왜 이름이 Lexical Scope 인가?
- Lexical Scope 라는 작명은 많은 사람들이 Lexical Scope 에 대해 이해하기 어렵게 만든다.
- 차라리 Static Scope 라는 이름이 훨씬 와닿는다.
영단어 중 Lexicon 이라는 단어가 있다. Lexicon 은 특정 분야, 개인, 집단에서 사용하는 어휘를 일컫는다. Lexical 은 Lexicon 의 형용사 형태로 단순히 '어휘의' 라는 의미를 가진다. 우리는 사실 Lexical 보다 Lexicon 의 의미에 집중해볼 필요가 있다. Lexicon 은 '특정 분야, 개인, 집단에서 사용하는' 어휘이다. 그 말은 전체가 쓴다기보다는 어떤 한정된 블록 내에서 사용한다는 뜻이다. Lexical Scope 를 '정의된 특정한 구역 내에서 사용하는 스코핑 방식' 정도로 해석하면 적당할 것이라 생각한다.
Lexical Scope (Static Scope) vs Dynamic Scope
- 두 방식을 비교하면 어떤 차이가 있는지 간단히 이해 된다.
Lexical Scope (Static Scope)
function getPersonName() {
let personName = "local jake"; // 지역 변수
return `my name is ${personName}`;
}
function printName() {
let name = getPersonName();
console.log(name);
return name;
}
printName();
- 아무런 문제 없는 정상적인 코드이다.
printName()
에서 자바스크립트 파서가 어떻게personName
을 해석하는지가Lexical Scope
의 핵심이다.- 런타임을 참조하지 않고, 정적으로 블록별 스코프 체인을 따라 전역 스코프까지 올라가서 변수의 이름을 찾아낸다.
- 이 경우엔
getPersonName()
함수 내부에서 쉽게 찾을 수 있었다.
- 이 경우엔
Dynamic Scope
function getPersonName() {
return `my name is ${personName}`;
}
function printName() {
let personName = "local jake"; // 지역 변수
let name = getPersonName();
console.log(name);
return name;
}
printName();
- 딱 봐도 오류가 발생할 것 같다.
- 그런데 다이나믹 스코프라는 전제 하에서는 유효한 코드일 수 있다.
- 다이나믹 스코프는 런타임에 변수가 체크된다.
- 사용해본적은 없지만,
Lisp
,Closure
(부분적으로) 와 같은 언어에서 사용된다고 한다.
레퍼런스
What is Lexical Scope
MDN - Lexical Scoping
Explain lexical scope in plain english
반응형
'자바스크립트 > 개념' 카테고리의 다른 글
매크로 태스크 (Macro Task) 와 마이크로 태스크 (Micro Task) 란? (0) | 2023.02.13 |
---|---|
자바스크립트의 실행 컨텍스트 (Execution Context) 란? (0) | 2023.02.05 |
이터러블 스프레드 문법이란? (0) | 2023.01.31 |
전개 구문, 속성 스프레드 구문 (Spread Syntax) 이란? (0) | 2023.01.02 |
자바스크립트 Object.assign() 메서드란? (0) | 2023.01.01 |