読み込み中...

JavaScriptのforEach&awaitをマスター!実用的な7つの応用例で徹底理解

JavaScriptのforEachとawaitを使った非同期処理のサンプルコード JS
この記事は約9分で読めます。

【サイト内のコードはご自由に個人利用・商用利用いただけます】

この記事では、プログラムの基礎知識を前提に話を進めています。

説明のためのコードや、サンプルコードもありますので、もちろん初心者でも理解できるように表現してあります。

本記事のサンプルコードを活用して機能追加、目的を達成できるように作ってありますので、是非ご活用ください。

※この記事は、一般的にプロフェッショナルの指標とされる『実務経験10,000時間以上』を満たす現役のプログラマチームによって監修されています。

※Japanシーモアは、常に解説内容のわかりやすさや記事の品質に注力しております。不具合、分かりにくい説明や不適切な表現、動かないコードなど気になることがございましたら、記事の品質向上の為にお問い合わせフォームにてご共有いただけますと幸いです。
(送信された情報は、プライバシーポリシーのもと、厳正に取扱い、処分させていただきます。)

●JavaScriptの非同期処理とは

JavaScriptプログラミングにおいて、非同期処理は極めて重要な概念です。

非同期処理とは、ある処理の完了を待たずに次の処理を実行する方法を指します。

この手法により、長時間かかる処理があっても、プログラムの実行が滞ることなく進行します。

JavaScriptでは、非同期処理を実現するためにPromiseやasync/awaitといった機能が用意されています。

機能を適切に活用することで、効率的かつ柔軟なプログラムの作成が可能となります。

○forEachとawaitの基本概念

forEachメソッドは、配列の各要素に対して指定された関数を実行するためのJavaScriptの組み込みメソッドです。

一方、awaitキーワードは、Promiseオブジェクトの解決を待機するために使用されます。

forEachとawaitを組み合わせることで、配列の各要素に対して非同期処理を順序よく実行することが可能になります。

この組み合わせは、多くの実践的なシナリオで非常に有用です。

●forEachとawaitの使い方

forEachとawaitの基本概念を理解したところで、実際の使用方法について詳しく見ていきましょう。

これらを組み合わせることで、非同期処理を効果的に制御できます。

ここでは、具体的なコード例を通じて、その実装方法を段階的に解説します。

○サンプルコード1:基本的な非同期処理

まずは、forEachとawaitを使用した基本的な非同期処理の例をご紹介します。

この例では、配列の各要素に対して1秒間隔で値を出力する非同期関数を実行します。

const asyncFunc = async (value) => {
  return new Promise((resolve) => {
    setTimeout(() => {
      console.log(value);
      resolve();
    }, 1000);
  });
};

const main = async () => {
  const array = [1, 2, 3, 4, 5];

  for (const value of array) {
    await asyncFunc(value);
  }
};

main();

このコードでは、asyncFunc関数が非同期処理を模擬しています。

main関数内では、配列の各要素に対してasyncFuncを呼び出し、その完了をawaitで待機しています。

●forEachとawaitの応用例

基本的な使い方を理解したところで、より実践的な応用例をいくつかご紹介いたします。

○サンプルコード2:APIリクエストの連続実行

次の例では、複数のAPIエンドポイントに対して順次リクエストを送信し、その結果を処理します。

const fetch = require('node-fetch');

const fetchData = async (url) => {
  const response = await fetch(url);
  const data = await response.json();
  console.log(data);
};

const main = async () => {
  const urls = ['https://api.example.com/data1', 'https://api.example.com/data2', 'https://api.example.com/data3'];

  for (const url of urls) {
    await fetchData(url);
  }
};

main();

このコードでは、fetchData関数が非同期でAPIリクエストを行い、取得したデータを出力します。

main関数内で、URLの配列に対して順次fetchDataを呼び出しています。

○サンプルコード3:並列実行制御

時には、複数の非同期処理を並列に実行したい場合があります。

const asyncFunc = async (value) => {
  return new Promise((resolve) => {
    setTimeout(() => {
      console.log(value);
      resolve();
    }, 1000);
  });
};

const main = async () => {
  const array = [1, 2, 3, 4, 5];

  const promises = array.map(asyncFunc);
  await Promise.all(promises);
};

main();

このコードでは、array.mapを使用して非同期処理を並列に開始し、Promise.allで全ての処理の完了を待機しています。

○サンプルコード4:エラーハンドリング

非同期処理を行う際、エラーハンドリングは非常に重要です。

次の例では、try-catch文を使用してエラーを適切に処理する方法を示します。

const asyncFunc = async (value) => {
  return new Promise((resolve, reject) => {
    setTimeout(() => {
      if (value === 3) {
        reject(new Error('Error occurred'));
      } else {
        console.log(value);
        resolve();
      }
    }, 1000);
  });
};

const main = async () => {
  const array = [1, 2, 3, 4, 5];

  for (const value of array) {
    try {
      await asyncFunc(value);
    } catch (error) {
      console.error(error);
    }
  }
};

main();

このコードでは、asyncFuncが特定の条件でエラーをスローするようになっています。

main関数内のtry-catch文でこのエラーを捕捉し、適切に処理しています。

○サンプルコード5:再試行処理

ネットワークエラーなどの一時的な問題に対処するため、再試行処理は非常に有用です。

非同期処理が失敗した場合に再試行を行う方法を紹介します。

const asyncFunc = async (value) => {
  return new Promise((resolve, reject) => {
    setTimeout(() => {
      if (Math.random() < 0.3) {
        reject(new Error('Error occurred'));
      } else {
        console.log(value);
        resolve();
      }
    }, 1000);
  });
};

const retryAsyncFunc = async (value, retries) => {
  for (let i = 0; i < retries; i++) {
    try {
      await asyncFunc(value);
      return;
    } catch (error) {
      console.log(`Retry ${i + 1}...`);
    }
  }
};

const main = async () => {
  const array = [1, 2, 3, 4, 5];

  for (const value of array) {
    await retryAsyncFunc(value, 3);
  }
};

main();

このコードでは、asyncFuncがランダムにエラーを発生させます。

retryAsyncFunc関数は、指定された回数だけ処理の再試行を行います。

○サンプルコード6:進捗表示

長時間かかる処理を実行する際、進捗状況を表示することでユーザーに適切なフィードバックを提供できます。

次の例では、処理の進捗を表示しています。

const asyncFunc = async (value) => {
  return new Promise((resolve) => {
    setTimeout(() => {
      console.log(value);
      resolve();
    }, 1000);
  });
};

const main = async () => {
  const array = [1, 2, 3, 4, 5];

  for (const [index, value] of array.entries()) {
    console.log(`Processing ${index + 1}/${array.length}...`);
    await asyncFunc(value);
  }
};

main();

このコードでは、array.entries()を使用して配列の各要素のインデックスを取得し、現在の進捗状況を表示しています。

○サンプルコード7:結果の整形

非同期処理の結果を収集し、整形して表示することも重要です。

この例では、非同期処理の結果を配列に格納し、最後にまとめて表示しています。

const asyncFunc = async (value) => {
  return new Promise((resolve) => {
    setTimeout(() => {
      resolve(value * 2);
    }, 1000);
  });
};

const main = async () => {
  const array = [1, 2, 3, 4, 5];
  const results = [];

  for (const value of array) {
    const result = await asyncFunc(value);
    results.push(result);
  }

  console.log(results);
};

main();

このコードでは、asyncFuncが入力値を2倍にして返します。

main関数内で、各非同期処理の結果をresults配列に格納し、全ての処理が完了した後にまとめて結果を表示しています。

まとめ

本記事では、JavaScriptにおけるforEachとawaitを使用した非同期処理について、基本的な概念から実践的な応用例まで幅広く解説いたしました。

この技術を適切に活用することで、効率的で堅牢なプログラムの作成が可能となります。

非同期処理は現代のWeb開発において欠かせない要素であり、本記事で紹介した手法を参考に、皆様のプロジェクトに最適な実装を検討していただければ幸いです。