基礎から学ぶJavaScript入門 90日コース | 非同期処理とAPI - Day 56:同期処理と非同期処理

JavaScript 90日で身につけるJavaScript
スポンサーリンク
スポンサーリンク

Day 56:同期処理と非同期処理

Day 56では、第5フェーズ「非同期処理とAPI」の最初の学習として、同期処理と非同期処理を学びます。ここから先は、これまでのDOM操作や localStorage 中心の学習とは少し感覚が変わってきます。第4フェーズまでは、主に「自分のプログラムの中で完結する処理」が中心でした。たとえば、ボタンを押したら画面を変える、入力した文字を保存する、配列を検索する、といった処理です。これらは、基本的にその場ですぐ終わる処理が多く、書いた順番に動くことを素直に理解しやすいものでした。

しかし、第5フェーズでは、外部とのやり取りが入ってきます。たとえば、APIからデータを取得する、サーバーへリクエストを送る、少し時間のかかる処理が終わるのを待つ、といった場面です。ここで必要になるのが非同期処理という考え方です。初心者の方にとっては、この非同期処理がJavaScript学習の最初の大きな壁の1つになりやすいです。なぜなら、「上から順に読めばその順番で動く」という今までの感覚だけでは説明しきれない動きが出てくるからです。

そこでDay 56では、いきなり fetch() や async/await に入るのではなく、まず「同期処理とは何か」「非同期処理とは何か」「なぜ非同期処理が必要なのか」という土台から丁寧に理解していきます。ここで大切なのは、難しい専門用語を丸暗記することではありません。大事なのは、「待つ処理があるときに、プログラム全体を止めないための考え方」が非同期処理なのだとつかむことです。今回も、日常のたとえや簡単なコード例を交えながら、ステップバイステップで整理していきます。

まず最初に結論をつかむ

最初に、今回の一番大事な結論をシンプルに言うと、同期処理は「順番に1つずつ終わらせる処理」、非同期処理は「時間のかかる処理を待っている間も、他のことを進められる処理」です。

この違いをイメージできるようになることがDay 56の大きな目標です。初心者の方は、まずこの1文を頭の中心に置いておくと、そのあとの説明がつながりやすくなります。

同期処理とは何か

同期処理とは、プログラムが上から下へ、書かれた順番に1つずつ処理を進めていく考え方です。前の処理が終わるまで次の処理には進みません。つまり、「今の処理が終わるのを待ってから次へ行く」動きです。

たとえば、次のコードを見てください。

// 1番目の処理
console.log("朝起きる");

// 2番目の処理
console.log("顔を洗う");

// 3番目の処理
console.log("朝ごはんを食べる");
JavaScript

このコードは、上から順番にそのまま実行されます。結果は次の順番です。

  • 朝起きる
  • 顔を洗う
  • 朝ごはんを食べる

これはとてもわかりやすい動きです。初心者の方が最初にJavaScriptを学ぶときの多くの処理は、この同期処理として理解できます。

同期処理の特徴をかみ砕いて理解する

同期処理の特徴は、「順番がはっきりしていて理解しやすい」ことです。前の処理が終わる前に次へ進まないので、流れを追いやすいです。たとえば、変数に値を入れて、その値を使って計算し、その結果を表示するような処理では、同期処理がとても自然です。

// 数値を用意する
const a = 10;
const b = 20;

// 足し算する
const result = a + b;

// 結果を表示する
console.log(result);
JavaScript

このコードでは、a と b が用意される前に result は作れませんし、result ができる前に表示もできません。このように、順番通りに進むのが自然な処理は同期処理に向いています。

初心者の方は、これまで学んできた多くのコードが同期処理だったと気づくと、非同期処理との違いが見えやすくなります。

同期処理の弱点

同期処理はわかりやすい反面、弱点もあります。それは、時間のかかる処理があると、その処理が終わるまで次に進めないことです。もし途中で非常に重い処理や待ち時間の長い処理があると、プログラム全体が止まったように見えることがあります。

たとえば、極端な例として、長い時間かかる処理が間に入るとします。

// 1番目の処理
console.log("処理を開始します");

// 重い処理のイメージ
for (let i = 0; i < 1000000000; i++) {
  // 時間のかかるくり返し
}

// 2番目の処理
console.log("処理が終わりました");
JavaScript

この場合、重い処理が終わるまで次の console.log() は実行されません。初心者の方は、「順番を守ること」と「待ち時間が発生すること」はセットになりやすい、と考えるとわかりやすいです。

非同期処理とは何か

非同期処理とは、時間のかかる処理を待っている間も、プログラム全体を止めずに、他の処理を先に進められる考え方です。ここが第5フェーズの入口として非常に重要です。

初心者向けに簡単に言えば、非同期処理は「終わるまで待つ必要はあるけれど、その間ずっと立ち止まらなくてよい処理」です。たとえば、データをインターネットから取ってくる処理は、すぐ終わるとは限りません。サーバーの返事を待つ時間があります。その待ち時間のせいで、画面全体が止まってしまうと困ります。だから、返事を待っている間に他のことを進められるようにする必要があります。

非同期処理を日常生活でたとえる

非同期処理は、日常生活のたとえで理解するとかなりわかりやすくなります。たとえば、料理を考えてみます。お湯を沸かすのに3分かかるとします。この3分の間、鍋の前で何もしないのが同期処理に近い考え方です。一方、お湯を沸かしている間に野菜を切ったり、皿を準備したりするのが非同期処理に近い考え方です。

  • 同期処理:お湯が沸くまで何もしない
  • 非同期処理:お湯が沸くのを待ちながら別の作業を進める

このたとえはとても重要です。非同期処理は、「待たなくてよい」という意味ではありません。「待っている間、全体を止めない」という意味です。初心者の方は、この違いをしっかりつかむことが大切です。

setTimeout() で非同期処理を体験する

非同期処理の最初の体験として、setTimeout() は非常にわかりやすいです。setTimeout() は、一定時間がたったあとに指定した処理を実行する仕組みです。

// 1番目の処理
console.log("スタート");

// 2秒後に実行される処理
setTimeout(function () {
  console.log("2秒たちました");
}, 2000);

// 3番目の処理
console.log("エンド");
JavaScript

このコードの結果は、初心者の方が最初に予想するものと違うことがあります。実行順はこうなります。

  • スタート
  • エンド
  • 2秒たちました

なぜこうなるのでしょうか。それは、setTimeout() の中の処理が「あとで実行される予約」だからです。2秒待っている間、プログラム本体は止まらず、そのまま次の console.log("エンド") へ進みます。ここに非同期処理の感覚があります。

この動きがなぜ重要なのか

この setTimeout() の例で大切なのは、「コードに書かれた順番」と「実際に表示される順番」が必ずしも同じではないことがある、という点です。これが、初心者の方が非同期処理で最初に戸惑いやすい部分です。

ただし、ここで慌てる必要はありません。大切なのは、「時間のかかる処理は後で終わるので、その間に後ろの処理が先に進む」と考えることです。つまり、非同期処理では「待ち時間のある処理」と「それ以外の処理」が分かれて動くのです。

同期処理と非同期処理を比べてみる

ここで、同期処理と非同期処理の違いを整理してみます。

  • 同期処理は、前の処理が終わるまで次へ進みません。
  • 非同期処理は、時間のかかる処理を待っている間に他の処理を進められます。
  • 同期処理は流れが追いやすいです。
  • 非同期処理はアプリを止まりにくくできます。

初心者の方は、この違いを「順番重視」と「待ち時間の活用」として覚えると理解しやすいです。

なぜ非同期処理が必要なのか

ここがDay 56の中心です。なぜ非同期処理が必要なのかというと、時間のかかる処理のせいでアプリ全体が止まってしまうのを防ぐためです。特にブラウザ上のJavaScriptでは、画面が固まったように見えると、ユーザーにとって非常に使いにくいアプリになります。

たとえば、次のような場面で非同期処理が必要になります。

  • APIから天気情報を取得するとき
  • サーバーから商品一覧を読み込むとき
  • 画像や動画を読み込むとき
  • ファイルをアップロードするとき
  • 一定時間後にメッセージを表示するとき

これらはすぐ終わるとは限りません。ネットワークの状態やデータ量によって待ち時間が変わります。そのため、こうした処理を同期的に止めてしまうと、アプリ全体の反応が悪くなります。非同期処理は、その問題を避けるために必要です。

ブラウザで非同期処理が特に大切な理由

ブラウザでは、JavaScriptが画面操作とも深く関わっています。つまり、JavaScriptが重い処理で止まると、ボタンが押せない、入力できない、画面が更新されない、といった問題につながることがあります。これはユーザーにとってかなりストレスです。

だからこそ、ブラウザでのJavaScriptでは、待ち時間のある処理を非同期で扱うことがとても重要です。初心者の方は、「非同期処理はただ難しい仕組みなのではなく、使いやすいWebアプリを作るために必要な仕組み」だと理解すると学びやすいです。

簡単な比較コードで違いを感じる

ここでは、同期っぽい流れと非同期っぽい流れを並べて見てみます。

同期的に見える流れ

console.log("1番目");
console.log("2番目");
console.log("3番目");
JavaScript

この結果はそのままです。

  • 1番目
  • 2番目
  • 3番目

非同期が入る流れ

console.log("1番目");

setTimeout(function () {
  console.log("2秒後の処理");
}, 2000);

console.log("3番目");
JavaScript

この結果は次の順番です。

  • 1番目
  • 3番目
  • 2秒後の処理

初心者の方は、この違いを「予約された処理はあとで来る」と理解すると整理しやすいです。

学習で特に注意したい誤解

ここで、初心者の方がしやすい誤解を整理しておきます。

  • 非同期処理は順番がめちゃくちゃになる、というわけではありません。
  • 非同期処理は待たなくてよい、という意味ではありません。
  • 非同期処理は速くなる魔法ではありません。

正しくは次のように理解する必要があります。

  • 非同期処理は、待つ必要がある処理を「あとで結果を受け取る形」にしているだけです。
  • 待ち時間そのものが消えるわけではありません。
  • その待ち時間の間に、他の処理を進められるのが利点です。

ここを誤解すると、今後 Promise や async/await を学ぶときに混乱しやすくなります。

そのまま試せる学習テンプレート

ここでは、同期処理と非同期処理の違いを体験できるシンプルなテンプレートを紹介します。

<!DOCTYPE html>
<html lang="ja">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Day 56 同期処理と非同期処理</title>
</head>
<body>
  <h2>同期処理と非同期処理の確認</h2>

  <button id="syncButton">同期処理を試す</button>
  <button id="asyncButton">非同期処理を試す</button>

  <p id="message">ここに結果が表示されます。</p>

  <script>
    // 必要な要素を取得する
    const syncButton = document.getElementById("syncButton");
    const asyncButton = document.getElementById("asyncButton");
    const message = document.getElementById("message");

    // 同期処理の例
    syncButton.addEventListener("click", function () {
      // 最初のメッセージを表示する
      console.log("同期処理:スタート");

      // 順番にメッセージを表示する
      console.log("同期処理:1つ目");
      console.log("同期処理:2つ目");
      console.log("同期処理:3つ目");

      // 画面に結果を表示する
      message.textContent = "同期処理は上から順番に実行されました。";
    });

    // 非同期処理の例
    asyncButton.addEventListener("click", function () {
      // 最初のメッセージを表示する
      console.log("非同期処理:スタート");

      // 2秒後に実行される処理を予約する
      setTimeout(function () {
        console.log("非同期処理:2秒後の処理");
        message.textContent = "2秒後の処理が終わりました。";
      }, 2000);

      // setTimeout を待たずに次へ進む
      console.log("非同期処理:先に進みます");

      // すぐに画面に表示する
      message.textContent = "非同期処理を開始しました。2秒後に続きます。";
    });
  </script>
</body>
</html>

このテンプレートでは、同期処理と非同期処理の違いを実際に確認できます。初心者の方は、ボタンを押しながら console.log() の順番を見てみると、非同期処理の感覚がかなりつかみやすくなります。

これから何につながるのか

Day 56で学ぶ内容は、これからの第5フェーズ全体の土台になります。今後学ぶ setTimeout() の応用、コールバック、Promise、async/await、そして fetch() を使ったAPI通信は、すべて非同期処理の考え方につながっています。つまり、Day 56は単独の回ではなく、この先の理解を大きく左右する基礎回です。

初心者の方は、ここで「非同期処理とは何か」をあいまいにしたまま進むより、少し時間をかけてでも感覚をつかんでおくほうが、後半がずっと楽になります。

初心者が特に注意したいポイント

Day 56では、次の点を特に意識すると理解が深まりやすいです。

  • 同期処理は、前の処理が終わるまで次へ進まない処理です。
  • 非同期処理は、待ち時間のある処理を待っている間に他の処理を進められる処理です。
  • `setTimeout()` は非同期処理の基本例として非常にわかりやすいです。
  • 非同期処理では、コードの見た目の順番と実行結果の順番がずれることがあります。
  • 非同期処理は、待ち時間をなくすのではなく、待っている間も止まらないようにする仕組みです。

特に重要なのは、「非同期=速い」ではなく、「非同期=止まりにくい、待ち時間をうまく扱える」という理解です。

情報セキュリティの観点での注意

Day 56の段階ではまだ外部API通信までは本格的に入りませんが、非同期処理は今後サーバーや外部サービスとの通信で頻繁に使うようになります。そのため、処理があとで返ってくるという特徴を理解しておくことは、セキュリティ面でも大切です。たとえば、通信結果が返る前に画面側の状態が変わることもあり、想定しない表示や操作のズレが起こることがあります。初心者の方は、非同期処理では「時間差がある」という前提を持つことが、安全で正確な設計につながると覚えておくとよいです。

Day 56のゴールを整理する

Day 56では、次のことができるようになっていれば十分です。

  • 同期処理とは何かを説明できる
  • 非同期処理とは何かを説明できる
  • なぜ非同期処理が必要なのかを説明できる
  • `setTimeout()` を使った非同期処理の基本例を理解している
  • コードの順番と実行結果の順番がずれることがあると理解している

ここまでできれば、Day 56としてはとても順調です。第5フェーズの入口として必要な土台がしっかりできています。

まとめ

Day 56では、第5フェーズ「非同期処理とAPI」の最初の学習として、同期処理と非同期処理を学びました。同期処理は、前の処理が終わるまで次へ進まない、順番通りの処理です。一方で非同期処理は、時間のかかる処理を待っている間にも他の処理を進められる仕組みであり、特にブラウザ上で止まりにくく使いやすいアプリを作るために重要です。setTimeout() を使った例では、コードに書かれた順番と実際の実行順がずれることがあり、ここに非同期処理らしい動きが表れます。

特に大切なのは、非同期処理は待ち時間を消す魔法ではないということです。待つ必要がある処理はやはり待つ必要がありますが、その間にプログラム全体を止めず、他のことを進められるようにしているのが非同期処理です。この考え方は、この先の Promise、async/await、fetch()、API通信の理解にそのままつながっていきます。

次に進む前に、今回のテンプレートを実際に動かし、console.log() の順番を何度も確認してみるのがおすすめです。そして、「なぜこの順番になるのか」を自分の言葉で説明できるようになると、第5フェーズの学習がかなり進めやすくなります。

タイトルとURLをコピーしました