Promise를 이용한 숫자up,down 만들어보자

이경준·2020년 11월 23일
0

Promise

비동기라는 것을 이해하는데 쉽지 않았다. 이벤트루프라는것이 존재하고 콜백이벤트는 큐로 빠져서 스택이 끝나야 순차적으로 스택으로 옮겨지고 실행된다..? 말이 쉽지 코드가 복잡해지면 머릿속도 같이 복잡해진다.

Promise는 비동기적인 이벤트루프를 효과적으로 다루기 위한 문법이다. then과 catch로 성공과 에러를 단계적으로 움직이게 할 수 있으며, async/await으로 가독성을 높일 수 있다.

연습1) 1초뒤 input값의 숫자가 plus,minus되는 버튼을 만들자

  • HTML
<button id="plus"> + </button>
<input id="input-text" type="text" />
<button id="minus"> - </button>
  • JS
const plus = document.querySelector("#plus");
const minus = document.querySelector("#minus");
const inputText = document.querySelector("#input-text");

plus.addEventListener("click", function () {
  return new Promise(function (resolve) {
    setTimeout(function () {
      const a = Number(inputText.value) + 1;
      inputText.value = a;
      resolve();
    }, 1000);
  });
});

minus.addEventListener("click", function () {
  return new Promise(function (resolve) {
    setTimeout(function () {
      const a = Number(inputText.value) - 1;
      inputText.value = a;
      resolve();
    }, 1000);
  });
});

html태그를 하나씩 불러온다음 addEventListener를 사용하여 클릭 버튼을 완성하였다. 그러나 Promise가 같은 기능을 하는데 중복되는 것이 불필요해 보였고, Async/await를 사용하지 않았다. 물론 사용하지 않아도 문제는 없었다.

연습2) 리팩토링

const delayPromise = function (n) {
  return new Promise(function (resolve) {
    setTimeout(function () {
      resolve(n);
    }, 1000);
  });
};

plus.addEventListener("click", async function () {
  const plusValue = Number(inputText.value) + 1;
  const value = await delayPromise(plusValue);
  inputText.value = value;
});

minus.addEventListener("click", async function () {
  const minusValue = Number(inputText.value) - 1;
  const value = await delayPromise(minusValue);
  inputText.value = value;
});

1초후에 n값을 갖는 promise함수를 따로 만들었다.
그리고 클릭 이벤트안에 +or-1한 값을 await delayPromise안에 넣어서 완성되게 하였다.
처음엔 resolve()의 이해가 부족해서 어려웠지만 resolve()값이 n값으로 뱉어내기때문에 마지막inputText.value를 컨트롤 할 수 있다는 것이 중요하다.


연습3) Promise.all을 사용하여 최적화 하기 (연습1,2와 관계없음)

const foo = function (n) {
  return new Promise(function (resolve) {
    setTimeout(function () {
      resolve(n);
    }, 2000);
  });
};

const bar = function (n) {
  return new Promise(function (resolve) {
    setTimeout(function () {
      resolve(n);
    }, 2000);
  });
};

const baz = function (n, m) {
  return new Promise(function (resolve) {
    setTimeout(function () {
      resolve(n + m);
    }, 3000);
  });
};

const result = async function () {
  const [result1, result2] = await Promise.all([foo(1), bar(2)]);
  console.log(result1, result2);
  const result3 = await baz(result1, result2);
  console.log(result3);
};

result();
//약2초 후 1,2가 출력되고 다시3초 후 3이 출력됨

3초마다 값이 출력되는 3개의 함수이다. 그러나 의도한 것은 baz의 값이 3초뒤에 출력되는 것이 중요하게 짜고 싶었다. 그렇다면 foo와 bar의 값으로 4초를 기다릴 필요가 없다고 생각했고 두 함수를 Promise.all을 이용하여 합쳐서 2초를 없앴다. 순서가 불필요한 함수는 합쳐서 불필요하게 여러번 도는 것을 없애서 깔끔한 코드를 만들 수 있다.
그러나 Promise.all은 하나라도 실패하면 모두 다 실패한다는 큰 특징이 있기 때문에 주의하여 사용 하여야 한다.

profile
내가 기억하기위한 블로그

0개의 댓글