호출 스택과 이벤트 루프
호출 스택
•
함수들이 실행되는 공간
백그라운드
→ 타이머, 이벤트 리스너의 공간
•
백그라운드는 타이머를 처리하고 이벤트 리스너를 저장하는 공간이다.
•
setTimeout 같은 함수를 실행하면 백그라운드에서 시간을 재고, 시간이 되면 setTimeout의 콜백 함수를 태스크 큐로 보낸다
•
또한 addEventListener로 추가한 이벤트를 저장했다가 이벤트가 발생하면, 콜백 함수를 태스크 큐로 보낸다
•
백그라운드에서 코드를 실행하는 것이 아니라, 실행될 콜백 함수들이 태스크 큐로 들어간다는 것 기억하기!
태스크 큐
→ 타이머나 이벤트 리스너의 콜백함수들이 들어가 있는 공간
•
태스크 큐는 실행되어야 할 콜백 함수들이 줄을 서서 대기하고 있는 공간이다.
•
큐라는 단어가 줄이라는 뜻 (FIFO)
•
다만, 태스크 큐도 함수를 직접 실행하지 않는다. 함수는 모두 호출 스택에서만 실행된다. 호출 스택에 들어온 함수가 호출(실행) 된다고 생각하면 된다.
이벤트 루프
→ 호출 스택이 비어있을 때, 태스크 큐에서 하나씩 꺼내서 실행시켜주는 역할
•
태스크 큐에서 호출 스택으로 함수를 이동시키는 존재가 바로 이벤트 루프이다.
•
호출 스택이 비어 있으면, 이벤트 루프는 태스크 큐에서 함수를 하나씩 꺼내(들어온 순서대로) 호출 스택으로 옮긴다.
•
호출 스택으로 이동한 함수는 그제서야 실행된다.
•
실행이 완료된 함수는 호출 스택에서 빠져나가게 되고, 호출 스택이 비면 이벤트 루프는 태스크 큐에 있는 다음 함수를 호출 스택으로 옮긴다.
예제)
function a() {
b();
}
function b() {
console.trace();
}
a();
JavaScript
복사
•
이 코드는 function anonymous 함수 안에 존재한다고 생각!
•
a 함수가 실행되고, 그 안에서 b 함수가 실행된다. 그리고 b 함수 안에서 console.trace 메소드가 실행된다. console.trace는 함수의 호출 스택을 보여주는 메소드이다.
실행 결과
→ console.trace는 호출 스택을 출력해주는 함수이다
console.trace
b
a
(anonymous)
Plain Text
복사
예제 2)
function aaa() {
setTimeout(() => {
console.log('d');
}, 0);
console.log('c');
}
setTimeout(() => {
console.log('a');
aaa();
}, 0);
setTimeout(() => {
aaa();
console.log('b');
}, 0);
// 호출 스택: anonymous -> setTimeout(끝) -> setTimeout(끝) -> anonymou(끝)
// 백그라운드: 타이머1-0초, 타이머 2-0초
// 태스크 큐: 타이머1-0초(여기에 있다가 백그라운드 비어있으면 옮겨준다), 타이머2-0초
// 콘솔: a, c, c, b, d, d
JavaScript
복사
→ latentflip을 이용하면 이벤트 루프의 원리를 시각적으로 볼 수 있다