Skip to content

동시성과 병렬성 한 장에 정리

동시성

동시성은 동시에 얼마나 다양한 일들을 컨트롤할 수 있는지!

예를 들어 웹 브라우저에서 동영상을 재생하고 있을 때, 플레이 리스트 스크롤이나 댓글 작성 등 다양한 일을 함께 할 수 있는 것이 동시성 구현이다.

웹 브라우저는 메인 스레드 하나로 동작한다. 때문에 버벅임 현상 최소화를 위해 Idle Time[1]을 확보하고, Long Task[2]를 최소화해야 한다.

용어 정의

  • [1] Idle Time: 메인 쓰레드의 작업이 없는 50ms 시간. 사용자 인터렉션이 발생할 수 있는 시간.
  • [2] Long Task: 50ms 이상 메인 쓰레드의 실행 시간

병렬성

병렬성은 동시에 얼마나 많은 일들을 할 수 있는지!

예를 들어 자바스크립트로 약 5초 걸리는 작업[1]을 웹 워커 5개로 실행[2]하면 좀 더 빠른 시간에 완료할 수 있다.

[1] 자바스크립트로 약 5초 걸리는 작업

js
const sumRange = ([start, end]) => {
  let total = 0;
  for (let i = start; i <= end; i++) {
    total += i;
  }
  return total;
};


console.time('sumRange');
sumRange([0, 10_000_000_000]);
console.timeEnd('sumRange');

// sumRange: 5089.886962890625 ms

[2] 웹 워커 5개로 실행

js
const sumRange = ([start, end]) => {
  let total = 0;
  for (let i = start; i <= end; i++) {
    total += i;
  }
  return total;
};

const runWorker = (fn, arg) => {
  return new Promise(resolve => {
    const blob = new Blob([`onmessage =e=>postMessage((${fn})(e.data));`], {
      type: 'text/javascript'
    });
    const url = URL.createObjectURL(blob);
    const worker = new Worker(url);
    worker.onmessage = e => resolve(e.data);
    worker.onerror = e => resolve(null);
    worker.postMessage(arg);
  });
};

console.time('runWorker');
Promise.all([
  runWorker(sumRange, [0, 2_000_000_000]),
  runWorker(sumRange, [2_000_000_001, 4_000_000_000]),
  runWorker(sumRange, [4_000_000_001, 6_000_000_000]),
  runWorker(sumRange, [6_000_000_001, 8_000_000_000]),
  runWorker(sumRange, [8_000_000_001, 10_000_000_000]),
])
  .then(results => {
    results.reduce((a, b) => a + b, 0);
    console.timeEnd('runWorker');
    // runWorker: 1597.4150390625 ms
  });