👹

async/awaitで処理を順番通りに出したい時の書き方

2021/07/16に公開

説明はほとんどないです。書き方を見て感じてください。👹

事前知識

全部同じ結果になる

コールバック関数を使うsetTimeout

setTimeout( function(){ console.log(3) } ,1000 );
setTimeout( function(){ console.log(2) } ,2000 );
setTimeout( function(){ console.log(1) } ,3000 );
setTimeout( () => console.log(3) ,1000 );
setTimeout( () => console.log(2) ,2000 );
setTimeout( () => console.log(1) ,3000 );

コールバック地獄

setTimeout( function() {
  console.log(3);
  setTimeout( function() {
    console.log(2);
    setTimeout( function(){
      console.log(1);
    },1000);
  },1000);
} ,1000);
setTimeout( function() { console.log(3);
  setTimeout( function() { console.log(2);
    setTimeout( function(){ console.log(1); },1000); },1000); } ,1000);
setTimeout( () => {
  console.log(3);
  setTimeout( () => {
    console.log(2);
    setTimeout( () => {
      console.log(1);
    },1000);
  },1000);
} ,1000);

Promise

new Promise(resolve => {
  setTimeout(() => {
    console.log(3);
    resolve();
  },1000);
}).then(() => {
  return new Promise(resolve => {
    setTimeout(() => {
      console.log(2);
      resolve();
    },1000)
  });
}).then(() => {
  return new Promise(resolve => {
    setTimeout(() => {
      console.log(1);
      resolve();
    },1000)
  });
});

async/await

func = async() => {
  await log(3);
  await log(2);
  await log(1);
}

log = (num) => {
  return new Promise(resolve => {
    setTimeout(()=>{
      console.log(num);
      resolve();
    },1000)
  });
}

func();

本題

二つの処理の順番を変える

非同期に処理される

function lightTask() {
  console.log("HIRO.です。");
}
 
function heavyTask() {
  const procedure = () => {
    console.log("僕の名前は");
  }
  setTimeout(procedure, 1000);
}
 
function sample() {
  heavyTask();
  lightTask();
}
 
sample();

順番に処理される

function lightTask() {
  console.log("HIRO.です。");
}

function heavyTask() {

  return new Promise((resolve) => {//Promise型を返す

    function procedure() {
      console.log("僕の名前は");
      resolve();
    }

    setTimeout(procedure, 1000);

  });

}

async function sample() {
  await heavyTask();
  lightTask();
}

sample();
  • awaitで呼び出される関数ではpromiseオブジェクトを返す必要がある
  • returnではなくresolveで戻す(これを忘れると制御が戻らない)
  • awaitを使用する関数にはasyncをつける
  • awaitで呼び出すことで処理が終わるまで待つ

thenメソッドを使う

function lightTask() {
  console.log("HIRO.です。");
}

function heavyTask() {

  return new Promise((resolve) => {//Promise型を返す

    function procedure() {
      resolve("僕の名前は");
    }

    setTimeout(procedure, 1000);

  });

}

async function sample() {
  await heavyTask().then(
    (value)=>{console.log(value);}//heavyTaskが終わってからじゃないとconsole.logは表示されない
  );
  lightTask();
}

sample();
GitHubで編集を提案

Discussion