[javascript] 비동기처리의 이해

Gangsan O·2022년 4월 12일
0

비동기?

  • 동기
    • 요청과 결과가 동시에 일어남 → 요청한 자리에서 결과가 주어져야함
    • 순차적으로 진행되기 때문에 설계가 간단하고 직관적임
    • 요청의 결과가 주어질 때까지 아무것도 하지 않고 대기하기 때문에 비 효율적일 수 있음
  • 비동기
    • 요청과 결과가 동시에 일어나지 않음 → 요청한 자리에서 결과가 주어지지 않음
    • 요청의 결과가 주어질 때까지 대기하지 않고 다른 작업을 할 수 있음

동기와 비동기의 개념과 차이

싱글 스레드 방식에서 비동기 처리하기

  • 자바스크립트는 한 번에 하나씩 일을 처리하는 싱글 스레드 방식으로 작동함
    • 코드 한 줄을 실행할 때 다음 줄의 코드는 이전 코드가 끝날 때까지 대기함
    • 만약 앞부분에 무거운 작업이 있다면 그 이후의 작업들은 먼저 있는 무거운 작업이 끝날 때까지 대기해 비효율을 야기 → 비동기로 처리하면 어떨까
  • 자바스크립트를 비동기적으로 처리하려면 싱글 스레드 방식의 자바스크립트 엔진만으로는 불가능함
    • 이를 해결하기 위해 자바스크립트 엔진은 콜백 패턴을 사용

콜백 패턴

  • 콜백(콜백함수) : 매개변수로 전달되는 함수
  • 자바스크립트 엔진은 비동기 처리를 하기 위해 콜백과 호출 스케줄링을 엔진 외부로 전달함
    • 이 때 엔진 외부는 호스트 환경(브라우저 혹은 nodejs)에 따라 달라질 수 있음
    • 브라우저 환경은 엔진 외부가 WebAPI이고 이곳에 콜백과 호출 스케줄링이 전달됨
    • 호출 스케줄링 : 콜백이 언제 호출(실행)되어야 할지 계산하는 작업
  • 자바스크립트 엔진은 콜백을 엔진 외부에 전달 한 뒤 해당 함수를 즉시 콜 스택에서 pop하고 다음 코드를 실행함
    • 호출 스케줄링 작업은 콜 스텍의 작업과는 별개로 독립적으로 실행되기 때문에 비동기적으로 처리됨
    • 호출 스케줄링 작업이 종료된, 즉, 실행되어야 하는 콜백은 테스크 큐에 들어감

태스크 큐와 이벤트 루프

  • 호출 스케줄링 작업이 끝나고 콜백함수가 불려야 할 시기가 되었을 때 WebAPI는 태스크 큐에 콜백을 push
    • 태스크 큐(task queue) : 호출할 시기가 된 콜백들이 대기하는 곳
  • 콜백도 결국 자바스크립트 함수이기 때문에 자바스크립트 엔진, 즉 콜 스택에서 실행되어야 함
    • 태스크 큐에서 콜 스텍으로 콜백이 전달 되어야 하는데 이 때 이벤트 루프가 그 역할을 함
    • 이벤트 루프 : 콜 스택이 완전히 비어있는지 확인 후 태스크 큐에서의 우선순위에 따라 콜백을 콜 스택에 올리는 역할을 수행
      • 태스크 큐의 우선순위는 크게 두 가지로 마이크로 태스크 큐와 매크로 태스크 큐가 있음
      • 마이크로 태스크 큐는 ES6부터 나온 프로미스 객체의 콜백 함수들의 대기 공간
      • 마이크로 태스크 큐가 매크로 태크스 큐 보다 우선순위가 높습니다.
    • 콜백 함수는 결국 콜 스택이 모두 종료 된 후에 실행됨 → 이러한 과정 때문에 호출 스케줄링에서의 시간은 최소 지연 시간만을 보장할 뿐 정확한 호출 시간을 보장하진 않음

이벤트 루프와 매크로·마이크로태스크

애니메이션으로 이해하는 이벤트루프

What the heck is the event loop anyway? | Philip Roberts | JSConf EU

콜백 패턴 활용

  • js는 무거운 작업이 있을 때 해당 작업이 끝날 때 까지 다른 작업은 할 수 없음
  • 이를 block된다고 표현하는데 non-block을 위해 비동기 방식을 사용할 수 있음
  • 무거운 작업을 작게 쪼개 작은 단위의 작업을 콜 스택에서 수행하고 나머지 작업을 콜백으로 넘김
  • 콜백으로 넘어갔기 때문에 콜 스택에서 대기하고 있는 나머지 작업들을 수행할 수 있게 됨
profile
감동 코딩

0개의 댓글