async/await
カフェで呼び出しベルを受け取って席でくつろぎ、ベルが鳴ったときだけ次の受け取りステップへ順番に進む賢い注文方式のようなものです。
定義 asyncとawaitは、時間のかかる処理(非同期処理)を扱う際に、複雑なコードの代わりにまるで上から下へ順番に実行される文章のように読みやすく書けるようにするプログラミング構文です。処理が終わるまでプログラム全体を止めることなく、結果を受け取る順序を自然に整理してくれます。
呼び出しベルを持って待つカフェの注文
カフェでドリンクを注文し、店員さんが作り終えるまでカウンターの前でぼーっと立ち尽くしていたらどうなるでしょうか? 後ろに並んでいる他のお客さんは注文すらできず、お店全体がストップしてしまいますよね。コンピュータのプログラムも同じです。遠く離れたサーバーから大きな画像をダウンロードしたりデータを取得したりする処理は、思っている以上に時間がかかります。もしデータが届くまでコンピュータがすべての動作を止めてしまったら、画面が真っ白に固まってしまいます。
そこでコンピュータは、時間のかかる処理をどこかに任せておき、すぐに別の仕事からサクサクこなします。これを「非同期処理」と呼びます。呼び出しベルを手にして席に戻り、スマホを見ながら時間を有効に使うのと同じです。しかし従来のやり方では、「ダウンロードが終わったらAをして、Aが終わったらBをして、Bが終わったらCをする」といった指示を数珠つなぎのように書かなければなりませんでした。
こうなると、コードが右へ右へと押し出され、何が書いてあるか分からない階段状になってしまいます。エンジニアたちはこれを「コールバック地獄」と呼びました。asyncとawaitは、まさにこの複雑に入り組んだコードを1行ずつ上から下へスッキリ読めるように整理してくれる最もスマートな道具なのです。
asyncとawaitの完璧な役割分担
この2つのキーワードは、常にペアになって動きます。まず関数の名前の前につけるasync(エイシンク)は、「この関数の中には時間がかかる待機処理が含まれていますよ」とコンピュータに前もって知らせる案内看板です。このキーワードがついた関数は、結果を「未来に返します」という特別な箱(Promise)に自動的に包んで渡してくれます。
関数の中で実際に待つ必要がある処理の前には、await(アウェイト)をつけます。これは「この処理の結果が出るまで、ここでちょっとだけ待ってね」という一時停止サインです。サーバーから天気データを完全に受け取るまで、次の行へ進まずに落ち着いて待機するわけです。
ここで最も重要なのは、該当する関数の中だけで順番を待つだけであり、プログラム全体の画面や他の処理は一切ストップしないという点です。お客さんが席に座って友達とおしゃべりしていても裏のキッチンでコーヒーが作られるように、コンピュータは画面を滑らかに動かしたまま、バックグラウンドで着実にデータを受け取ります。
もう少し正確に言うと:シンタックスシュガーの魔法
もう少し正確に言うと、asyncとawaitはコンピュータの仕組みそのものをガラリと変えたまったく新しい技術ではありません。元々JavaScriptなどの言語で非同期処理を扱うために使われていた「Promise(将来的に値を返す約束のオブジェクト)」という構文を、人間がより読みやすい形に包んだ皮膜のようなものです。
プログラミングの世界では、このように中身の仕組みは同じまま、人間が読み書きしやすいように整えられた構文を「シンタックスシュガー(構文糖)」と呼びます。コンピュータの内部では依然として複雑な非同期のルールに従ってPromiseの箱をやり取りしていますが、コードを書くエンジニアの目には順番に1つずつ実行される普通のコードのように見えるようにしてくれるのです。
このような直感的な構造のおかげで、エラーへの対処もずっと簡単になりました。通常のプログラミングで使われる標準的なエラー処理構文(try-catch)をそのまま使って、ネット接続が切れたりサーバーに問題が発生したりした際に、どこでエラーが起きたのかを簡単に見つけて対処できるようになりました。
🤔 よくある誤解
awaitを使うとプログラム全体がストップして、ユーザーがボタンを押すことすらできなくなる。
awaitはその非同期関数の中にある次の行の実行を一時待機させるだけです。Webブラウザの画面描画やユーザーのマウスクリックなど、プログラム全体の動作は止まることなく正常に動き続けます。
async/awaitはPromiseを使わないようにするために作られた代替機能である。
async/awaitは内部的には依然としてPromiseをベースに動作しています。Promiseのコードを人間がより読みやすい形に包んでくれた「シンタックスシュガー(構文糖)」に過ぎません。
🧺 日常で出会う場面
時間のかかる非同期処理を、人間にとって読みやすい順序通りのコードとして書けるようにするプログラミング構文です。