동기와 비동기 처리?

SCYu·2022년 10월 14일
0

시작하며...

자바스크립트에서 중요한 개념은 차고 넘치지만, 그 중에서 처음 들었을 때 제일 이해하기 힘들었던 개념은 바로 동기(synchronous)와 비동기(Asynchronous) 처리였다. 그냥 말만 보면 흔히 말하는 클라우드에서의 동기화(synchronization) 같은건가, 하고 생각할 수도 있는데 이것과는 좀 다른 내용이다. 간단하게 말하면 동시에 무언가를 하는 것이 되냐, 안 되냐의 차이인데 밑의 글에서 조금더 자세히 다뤄보자.

<여기서의 동기는 클라우드의 동기화와는 많이 다르다..>

동기 처리란?

우선 동기 처리부터 알아보자. 현재 실행중인 테스크가 종료할 때까지 다음에 실행될 테스크가 대기하는 방식을 동기(synchronous) 처리라고 하는데, 이렇게만 해놓으면 무슨 소린지 이해가 안가니 예시를 들어보자.

function synchronous(func, delay) {
	const delayUtil=Date.now() + delay;
    while (Date.now() (&lt) delayUntil);
    func();
}
function a() {
	console.log('a');
}
function b() {
	console.log('b');
}
synchronous(a, 5*1000);
b();

위의 예시에서 어떤 결과가 나올까? synchronous 함수는 5초 뒤에 a 함수를 호출한다. 이때 b 함수는 a 함수의 실행이 종료된 이후에 호출되므로 5초 이상(a 함수의 실행 시간 + 5초) 호출되지 못하고 블로킹(작업 중단) 된다. b 함수가 a 함수가 종료될 때까지 실행되지 못하고 대기하는 것이다. 이런 과정을 동기 처리라고 하며, 비동기 처리보다 구현하기 쉽고 실행순서가 보장된다는 장점이 있지만 하나의 테스크가 종료될 때까지 이후 테스크들이 블로킹 처리되어 느리다는 단점이 있다.

비동기 처리란?

위의 동기 처리와는 달리, 비동기(Asynchronous) 처리는 현재 실행중인 테스크가 종료되지 않은 상태라도 다음 테스크를 바로 실행한다. 이번에도 예시를 들어보자.

function a() {
	console.log('a');
}
function b() {
	console.log('b');
}
setTimeout(a, 5*1000);
b();

위의 예시에서는 어떤 결과가 나올까? setTimeout 함수는 위의 synchronous 함수와 비슷하게 일정 시간 경과 후에 콜백 함수를 호출하지만, setTimeout 함수 이후의 테스크를 블로킹하지 않고 바로 실행한다. 이때 b 함수는 a 함수의 실행이 종료됐는지의 유무에 상관없이 바로 호출된다. 이런 과정을 비동기 처리라고 하며, 블로킹이 발생하지 않아 동기 처리보단 속도가 빠르다는 장점이 있지만, 실행순서가 보장되지 않으며 복잡하다는 단점이 있다.

여기서 주의해야 할 점은, 비동기 처리를 수행하는 비동기 함수는 전통적으로 콜백(CallBack) 패턴을 사용하는데, 이는 콜백 헬을 발생시켜 가독성을 떨어뜨린다. 또한 비동기 처리 중 에러와 예외 처리가 곤란하다는 등의 한계점들이 있기 때문에, 요즘에는 비동기 처리를 구현할 때 프로미스(Promise)를 도입하고 있다. 이는 다음 포스팅에서 살펴보자.

<동기와 비동기 처리의 개념를 너무나도 잘 나타내주는 그림...이 그림을 그리신 분은 분명 천재다!>

동기 처리의 이유?

그렇다면, 위의 상황에서 동기 처리는 도대체 왜 발생하는 것일까? 그 이유는 자바스크립트라는 언어의 특징에서 찾을 수 있다. 자바스크립트는 기본적으로 싱글스레드(single thread) 방식으로 동작한다. 여기서 스레드에 대한 자세한 내용까지 들어가면 글이 너무 길어지니 그건 다음 글에서 다루도록 하고, 간단하게 설명하자면 어떤 일을 할 때 필요한 "자원"같은 개념이다. 그리고 싱글스레드 방식은 이 스레드라는 자원이 한번에 여러개 실행되지 못하고 한개만 실행되기 때문에 테스크들도 한번에 하나씩만 할 수 있는 것이다. 이것이 바로 자바스크립트와 자바스크립트 엔진의 특징이며, 이 특징 때문에 동기 처리가 발생한다.

비동기 처리의 이유?

뭔가 이상하지 않은가? 자바스크립트는 기본적으로 싱글스레드 언어이기 때문에 테스크 하나가 실행중이면 다른 테스크는 블로킹당한다고 위에서 설명했다. 하지만, 현재 자바스크립트에서는 비동기 처리 또한 버젓이 쓰이고 있다. 이 모순적인 상황은 왜 발생하는 것일까? 바로 자바스크립트와는 달리 자바스크립트가 실행되는 환경인 브라우저가 멀티스레드(multi thread)를 지원하기 때문이다. 앞서 비동기 처리를 설명할 때 예시로 든 setTimeout 함수의 모든 처리가 자바스크립트 엔진에서 싱글 스레드로 수행된다고 가정해보자. 그러면 setTimeout 함수의 호출 스케줄링을 위한 타이머 설정도 싱글스레드 방식으로 작동할 것이고, 이는 결국 동기 처리가 되어버린다. 즉 브라우저와 자바스크립트가 협력하고 있기에 비동기 처리가 가능해지는 것이다.

<많은 것을 가능하게 해주는 브라우저...그의 한계는 어디까지인가?>

마치며...

오늘은 자바스크립트에서 제일 생소했었던 개념인 동기와 비동기 처리에 대해서 알아봤다. 싱글 스레드를 이용한, 한번에 한 테스크만 처리하는 동기 처리와 멀티 스레드를 이용한, 한번에 여러 테스크를 동시에 처리하는 비동기 처리는 앞으로 복잡한 개념들을 배울 때 초석이 되어 줄 것이다.

<오늘의 마지막은 은하수 사진으로 끝내고자 한다. 천체 사진을 보고 있으면 몽환적인 기분이 든다..>

profile
Front+Back=Full

0개의 댓글