Lexical Runtime

실행 컨텍스트와 클로저 연결 흐름

함수 호출은 새 실행 컨텍스트를 만들고, 함수 선언 위치는 렉시컬 환경의 연결을 남긴다. 클로저는 이 연결을 나중까지 보존한다.

global env outer 함수 선언 위치가 기준점이 된다.
outer() 호출 중 지역 변수와 내부 함수를 만든다.
inner closure 반환 뒤에도 필요한 환경만 붙잡는다.
call stack
outer() 실행 컨텍스트 호출 중에는 지역 변수와 내부 함수 선언을 함께 가진다.
return 뒤 스택 제거 함수 프레임은 사라지지만 필요한 환경은 남을 수 있다.
lexical environment
count 내부 함수가 계속 읽는 외부 변수
outer ref 선언 위치 기준으로 이어지는 바깥 환경 참조
closure object
반환된 내부 함수 나중 호출에서도 보존된 렉시컬 환경을 참조한다.
메모리 유지 단서 큰 객체 참조를 오래 붙잡는지 함께 확인한다.

실행 순서로 읽기

1

함수 호출

엔진은 새 실행 컨텍스트를 만들고 호출 스택 위에 올린다.

2

렉시컬 환경 구성

현재 변수와 외부 환경 참조가 묶여 스코프 체인을 이룬다.

3

내부 함수 반환

반환된 함수는 선언 당시의 외부 변수를 계속 참조할 수 있다.

4

나중에 다시 실행

스택에서 사라진 함수의 필요한 환경만 클로저로 남아 동작한다.

환경

변수는 환경에 저장된다

함수 안의 변수는 실행 컨텍스트의 렉시컬 환경에서 관리된다.

탐색

가까운 스코프부터 찾는다

현재 환경에 없으면 외부 환경 참조를 따라 전역까지 올라간다.

보존

참조 중인 환경은 남는다

내부 함수가 외부 변수를 쓰면 필요한 값은 회수되지 않는다.

클로저 보관 한계

불필요한 참조 축소

큰 객체를 오래 붙잡는 클로저는 메모리 유지 시간을 늘릴 수 있다.

검토 단서

클로저를 볼 때는 함수가 호출된 위치보다 선언된 위치, 그리고 반환된 함수가 어떤 외부 변수를 계속 읽는지를 먼저 확인한다.