
- 현재 실행 중인 코드에 대한 세부 정보(제어 흐름의 위치, 선언된 변수, 함수, this, arguments 등)을 담고 있는 데이터 구조
- 함수 실행, 호이스팅, 렉시컬 환경, 클로저 같은 개념을 관통하는 큰 개념
➡️ 현재 실행 중인 코드에 대한 정보를 담고 있음
global execution context : 전체 스크립트에 대한 실행 컨텍스트call stack에 push됨Function execution context : 호출된 함수에 대한 실행 컨텍스트호출될 때 call stack에 push됨함수가 호출될 때마다 실행 컨텍스트가 생기기 때문에 메모리를 많이 소요하고, 너무 많이 하면 Uncaught RangeError: Maximum call stack size exceeded 에러가 난다global execution context가 콜 스택에 push되고, 함수가 있다면 Function execution context로 콜 스택에 push된다pop되고, global의 경우 앱이 종료되면 스택에서 pop된다// 스크립트가 실행됨
// Global Execution Context가 call stack에 push됨
let name; // 렉시컬 환경의 EnvironmentRecord에 name: <uninitialized>로 올라감
function func1(name) {
console.log('hello');
// func2 호출 => func2 실행 컨텍스트 생성, call stack에 push
func2(name);
}
function func2(name) {
console.log('world!')
}
name = 'kaya' // EnvironmentRecord { name: 'kaya' }로 변경
// func1 호출 => 호출되었으니 Function Execution Context가 stack에 push됨
func1(name);
// func2가 먼저 실행이 완료되면 pop
// 그 다음 func1이 실행이 완료되면 pop
// script 전체가 종료되면 global execution context도 pop

Variable Environment, Lexical Environment,ThisBinding가 있다EnvironmentRecord 객체, outerEnvironmentReference로 구성this 키워드가 참조할 값이 할당됨 ➡️ this 바인딩 규칙에 따라 할당됨실행 컨텍스트의 일부이기 때문에, 스크립트가 실행될 때, 함수가 호출될 때 각각 렉시컬 환경이 생성된다
EnvironmentRecord 객체
(1) 변수
var로 선언: 렉시컬 환경에 올라갈 때 변수명: undefined로 올라간다let, const로 선언: 렉시컬 환경에 올라갈 때 변수명: <uninitialized>로 올라간다(2) 함수
EnviormentRecord {
name: <uninitialized>,
func1: Function,
func2: Function
}
outerEnvironmentReference전역 렉시컬 환경으로 확장될 때까지 반복됨기본적으로 모든 변수와 함수에서 호이스팅이 발생한다. 다만 그 선언 방법에 따라 호이스팅이 안되는 것처럼 보이는 게 있다
console.log(value) // undefined
var value;
value = 'hello'
value = 'world'
console.log(value) // 'world'
var로 변수를 선언하면 렉시컬 환경의 EnvironmentRecord에 value: undefined의 형태로 올라간다
즉 console.log(value) 코드를 실행할 때 value에 undefined라는 프로퍼티값이 할당되어 있으므로 undefined라는 결과가 나오게 된다
그리고 value = 'hello', value = 'world' 코드를 거치면서 EnvironmentRecord의 프로퍼티값이 'hello' ➡️ 'world'로 바뀐다
함수 선언문으로 선언한 함수도 렉시컬 환경에 바로 올라가기 때문에 호이스팅되는 것이다
console.log(value) // Uncaught ReferenceError: value is not defined
let value;
value = 'hello'
value = 'world'
let으로 변수를 선언하면 EnvironmentRecord에 value: <uninitialized> 형태로 올라간다let을 만나기 전까지 이 변수를 참조할 수 없다ReferenceError가 나는 것이다var로 선언하든, let으로 선언하든 둘 다 에러가 난다func4() // TypeError: func4 is not a function
console.log(typeof func4) // undefined
var func4 = function(){
console.log('hello js');
}
func4() // ReferenceError: Cannot access 'func4' before initialization
let func4 = function(){
console.log('hello js');
}
var로 선언하면 undefined로 올라가기에 TypeError가 나는 것이고let으로 선언하면 <uninitialized>로 올라가서 참조를 할 수가 없다는 ReferenceError가 발생하는 것이다