본문 바로가기
JavaScript

[Javascript] javascript에서의 동기와 비동기방식

by 쁘니쁘나 2021. 8. 1.

✨ 동기방식 & 비동기방식 이란?

javascript의 Promis, async, await를 배우며 콜백 함수, 동기방식, 비동기 방식이라는 용어가 등장하였다.

콜백 함수는 아래에 따로 작성해 놓았다.

https://mynameisleeminee.tistory.com/44

 

[Javascript] Callback 함수란 무엇일까?

✨ CALLBACK 함수란? Javascript 를 공부하던 도중 Callback 함수라는 것이 나왔다. Callback 함수가 도대체 무엇이길래 Callback, Callback 하는 것일까? 일단 내가 이해한 대로 정리해본다. • 말 그대로 콜백...

mynameisleeminee.tistory.com

그럼 오늘은 동기방식, 비동기 방식이 무엇인지 알아보도록 하자.

 

✨ 동기방식(Synchronous)

✔ 순서대로 동작하는 방식이다.
✔ 요청을 보내고 응답(결과)이 와야 다음 작업을 수행할 수 있다. 즉, 하나의 작업이 끝이 나야 다른 작업이 실행된다.
✔ 만약, 어떠한 데이터를 받을때까지 시간이 오래 걸린다면 사용자는 해당 데이터가 올 때까지 아무런 작업도 할 수 없다. 즉, 클라이언트와 서버 간의 교류가 있는 곳에서는 효율성이 떨어진다.

 

이제 코드를 보며 이해해보자.

 

function printHello() {
  console.log("Hello");
}

function printHi() {
  console.log("Hi");
}

printHello();
printHi();

// 결과
Hello
Hi

 

위의 코드에서 printHello(), printHi() 함수를 각각 호출하였다.

printHello() 먼저 선언되었기 때문에 printHello() 함수 내부의 "Hello"가 먼저 콘솔로그에 찍힐 것이고, 

그다음에 선언된 printHi() 함수가 실행되어 "Hi"가 찍힌다.

 

동기방식은 이렇게 먼저 선언된 함수부터 순서대로 실행되는 방식이다.

 

하지만 이러한 동기방식에는 단점이 있다. 

만약, 먼저 선언되 printHello()가 실행되어 결과를 내보낼 때까지 꽤 오랜 시간이 걸린다면? 그다음 선언된 printHi()는 printHello()의 작업이 끝날 때까지 실행되지 못하고 대기를 하게 된다.

 

사용자로 예를 들면, 웹사이트를 이용하는 사용자가 어떤 데이터를 보고자 화면에서 클릭했을 때 그것에 대한 응답이 늦게 온다면 사용자는 그 응답이 올 때까지 아무것도 못하는 상황에 놓이게 된다.

 

이러한 단점을 해결할 수 있도록 비동기 방식을 알아보자.

 

 

✨ 비동기 방식(Asynchronous)

✔ 병렬적. 즉, 동시에 다른 작업을 한 번에 할 수 있는 방식을 비동기 방식이라 한다.
✔ 다만, 각각의 작업이 서로 연관되어 있지 않을 때만 비동기 방식으로 처리를 해야 한다. 예를 들어 하나의 작업이 끝나고 난 후 받은 결과를 가지고 다음 작업을 수행해야 할 때는 비동기 방식이 아닌 동기방식을 사용해야 한다.
✔ 하나의 작업에서 결과를 받기까지 시간이 좀 소요되더라도 그동안 다른 작업을 병행할 수 있으므로 효율적이라 할 수 있다.

 

이제 코드를 보며 이해해보자.

 

function pirntA() {
  setTimeout(() => {
    console.log("AAA");
  }, 2000);
}

function pirntB() {
  setTimeout(() => {
    console.log("BBB");
  }, 1000);
}

pirntA();
pirntB();

// 결과 
BBB
AAA

 

위의 코드에서 printA(), pirntB() 순서대로 호출하였지만 결과는 printB()에서 실행된 BBB가 먼저 콘솔 로그에 찍힌다.

이유는 비동기 방식의 대표적인 함수인 setTimeout을 사용하였기 때문이다.

 

setTimeout과 같이 비동기 함수를 사용한다면 비동기 방식으로 처리가 되어 printA(), printB()가 동시에 실행되며 그중 먼저 작업이 끝나는 순서대로 결과가 나오게 된다. 

 

즉, 비동기 방식의 함수들은 동시에 시작되며 하나의 작업이 끝날 때까지 기다리지 않고 먼저 작업이 끝난 순서대로 결과를 보여주게 된다.

 

이렇게 비동기 방식으로 처리하면 사용자가 어떤 요청을 했을 때, 그 응답이 올 때까지 무한정 대기하는 현상을 예방할 수 있다.

하지만, 이런 비동기 방식은 서로 연관되어 있지 않은 작업에서 사용하여야 한다.

하나의 작업을 처리한 결과를 가지고 다른 작업에서 사용하여야 하는 경우에는 동기방식으로 처리를 하여야 한다.

 

 

💡 동기와 비동기 방식이 같이 들어가 있는 프로그램은 어떤 순서로 진행될까?

위에서 프로세스가 동기방식으로만 작성되어있다면 순서대로, 반대로 비동기 방식으로만 작성되어있다면 모두 동시에 실행되고 제일 먼저 끝나는 작업부터 실행이 되는 순서라는 것을 알 수 있었다.

 

그렇다면 동기방식과 비동기 방식이 같이 혼용되어있는 프로세스라면 어떤 순서로 진행될까? 

 

정답은 동기방식이 우선적으로 모두 실행되고 난 뒤, 그다음으로 비동기 방식이 진행되게 된다.

 

코드를 보며 이해해보자.

 

function pirntA() {  // 비동기방식
  setTimeout(() => {
    console.log("AAA");
  }, 2000);
}

function pirntB() {  // 비동기방식
  setTimeout(() => {
    console.log("BBB");
  }, 1000);
}

function printHello() {  // 동기방식
  console.log("Hello");
}

function printHi() {  // 동기방식
  console.log("Hi");
}

pirntA();
pirntB();
printHello();
printHi();

// 결과
Hello
Hi
BBB
AAA

 

비동기 방식과 동기방식이 같이 있는 위의 코드에서 printA(), pirntB()를 먼저 호출하더라도 아래의 printHello(), printHi()의 동기방식이 먼저 작업이 끝난 후 동작하게 되는 것을 알 수 있다.

 

비동기 방식의 효율적인 처리를 위한 Promis, async, await는 다음 포스팅에서 이해해보자.

 

 

댓글