동기와 비동기
동기는 이전의 작업이 끝나야 다음 것을 할 수 있지만, 비동기는 여러 작업을 동시에 진행할 수 있다.
자바스크립트는 동기 언어이다.
자바스크립트는 한 줄을 실행하고 다음 줄을 실행하는 ‘동기 언어’이다. 그런데 setTimeout 함수처럼 비동기로 작동하는 함수가 있다. 이는 자바스크립트의 부분이 아니다. 브라우저에서 사용을 한다면 브라우저 api를 사용하는 것이고, Node에서 사용한다면 Node api를 사용하는 것.
즉! 자바스크립트는 비동기처럼 사용할 수는 있지만, 결국은 다른 것의 도움을 받아서 비동기처럼 사용할 수 있는 것!
자바스크립트 동작 과정
자바스크립트 코드를 실행하려면 자바스크립트 엔진이 필요하다. 이때 엔진은 두 가지 주요 요소로 구성된다.
메모리 힙 - 메모리 할당이 발생하는 곳(변수를 정의하면 저장이 되는 창고)
호출 스택 - 코드가 실행될 때 스택들이 이곳에 쌓이게 됨
function B(){
setTimeout(function(){
console.log('B-1');
},1000);
};
function A(){
console.log('A-1');
B();
console.log('A-2');
};
A();
위의 코드가 실행될 때 Call Stack에서 진행되는 방식은 다음과 같다.
setTimeout 함수의 console.log는 출력이 되기 전에 갑자기 사라진다. 그리고 마지막에 다시 등장한다. 이때 setTimeout 함수가 어디로 갔다 왔는지 알아보겠다.
비동기 작업(DOM, AJAX, setTimeOut)은 Web API에서 처리해 준다. 즉 setTimeout함수가 갑자기 사라졌던 것은 Web API로 보내진 것이었다.
Web ApI에서 setTimeout의 시간이 완료되면 Callback Queue로 들어오게 된다. 이때 Callback Queue에는 Web API의 콜백 함수들이 대기한다.
이벤트 루프는 Call stack과 Callback Queue를 계속 주시하고 있다가, Call Stack이 비게 되면 먼저 들어온 순서대로 Callback Queue에 있는 함수들을 Call Stack에 넣어준다.
setTimeout의 지연시간이 0초라면 0초 후에 바로 실행될까?
결론부터 말하면 아니다.
console.log('1');
setTimeout(function(){
console.log('2');
},0);
console.log('3');
이벤트 루프는 Call Stack이 다 비워져 있어야 Callback Queue에 있는 콜백함수들을 이동시킨다. 즉 0초의 지연시간 이후 Callback Queue에서 대기하고 있을 때, Call Stack에 이미 어떠한 것이 있으면 계속 대기를 해야 한다.
0초 이후에 함수가 호출되는 것을 보장하는 것이지, 딱 0초가 지난 다음 함수 호출하는 것을 보장하는 것은 아니다.
'프로그래밍 언어 > JavaScript' 카테고리의 다른 글
[JS] 얕은 비교, 깊은 비교 / 얕은 복사, 깊은 복사 (0) | 2024.04.26 |
---|---|
[JS] 클로저 (2) | 2024.04.25 |
[JS] call, apply, bind 메서드 (0) | 2024.04.25 |
[JS] this 키워드 (0) | 2024.04.25 |
[JS] id를 반환받지 않아도 Script에서 바로 지목할 수 있다. (0) | 2024.04.24 |