Pythonのasyncによる非同期処理の仕組みと使い方をわかりやすく解説

スポンサーリンク
スポンサーリンク

asyncの概要

非同期処理の定義 Python予約語

async

概要 asyncはPythonで非同期処理を定義するための予約語です。async defを使うことで、通常の関数を非同期関数(コルーチン)として定義できます。

わかりやすく説明 asyncを使うと、待ち時間のある処理(例えばネットワーク通信やファイル読み込み)を効率的に処理できます。処理が完了するのを待っている間に、他の処理を並行して進めることができます。

  • async defを使うと、非同期関数(コルーチン)を定義できます。
  • 非同期関数内ではawaitを使い、処理の一時停止と再開を行います。
  • asyncasyncioライブラリと組み合わせて使われることが多いです。

asyncの基本的な使い方

async defを使って非同期関数を定義し、awaitを使って非同期処理を実行できます。

# 非同期関数の基本
import asyncio

async def say_hello():
    print("こんにちは!")
    await asyncio.sleep(2)  # 2秒待機(非同期)
    print("お待たせしました!")

# 非同期関数の実行
asyncio.run(say_hello())
  • async defを使って非同期関数を定義します。
  • await asyncio.sleep(2)は2秒間待機し、その間に他の処理を実行できます。
  • asyncio.run()を使って非同期関数を実行します。

asyncとawaitの組み合わせ

非同期関数の中で別の非同期関数を呼び出す場合、awaitを使って処理を待つことができます。

# asyncとawaitの組み合わせ
import asyncio

async def task1():
    print("タスク1開始")
    await asyncio.sleep(3)  # 3秒待機
    print("タスク1完了")

async def task2():
    print("タスク2開始")
    await asyncio.sleep(2)  # 2秒待機
    print("タスク2完了")

async def main():
    await asyncio.gather(task1(), task2())  # 並行実行

asyncio.run(main())
  • await asyncio.gather(task1(), task2())を使うと、タスクを並行して実行できます。
  • タスク1とタスク2が同時に開始し、それぞれの処理が完了すると次の処理が進みます。

asyncの実践的な使用例

非同期処理を使うと、複数のWebリクエストを同時に実行することができます。

# 非同期で複数のURLを取得
import asyncio
import aiohttp  # 非同期HTTPリクエスト用ライブラリ

async def fetch(url):
    async with aiohttp.ClientSession() as session:
        async with session.get(url) as response:
            return await response.text()

async def main():
    urls = ["https://example.com", "https://example.org"]
    tasks = [fetch(url) for url in urls]
    results = await asyncio.gather(*tasks)
    for result in results:
        print(result[:100])  # 最初の100文字を表示

asyncio.run(main())
  • aiohttpライブラリを使って非同期でWebページを取得します。
  • async withを使うことで、非同期のコンテキストマネージャを利用できます。
  • asyncio.gather()を使って複数のリクエストを並行実行します。

asyncの注意点

  • 非同期関数の実行にはasyncio.run()が必要: async関数は通常の関数のように直接呼び出せません。
  • 同期処理とは混在させない: async関数の中では、ブロッキングする処理(例えば通常のtime.sleep())は避けるべきです。
  • 一部のライブラリは非同期に対応していない: すべてのライブラリが非同期処理をサポートしているわけではないため、非同期版のライブラリを使う必要があります。

asyncのよくある質問

Q: asyncを使うメリットは何ですか?
A: I/O待ち時間が発生する処理(ネットワーク通信、ファイル入出力、データベースアクセスなど)を効率的に処理できます。
Q: async関数を直接呼び出すとどうなりますか?
A: 非同期関数を通常の関数のように呼び出すと、コルーチンオブジェクトが返り、実行されません。awaitまたはasyncio.run()を使う必要があります。
Q: 非同期処理は並列処理と同じですか?
A: いいえ。非同期処理は「並行処理」であり、スレッドやプロセスを増やして並列実行するわけではありません。1つのスレッド内でタスクの切り替えを行います。

まとめ

asyncは、Pythonで非同期処理を行うためのキーワードであり、待ち時間のある処理を効率的に扱うのに適しています。

  • 非同期関数を定義するにはasync defを使います。
  • 非同期関数の中ではawaitを使って処理を一時停止できます。
  • 複数の非同期タスクを並行して実行するにはasyncio.gather()が便利です。

非同期処理を適切に活用し、効率的なプログラムを作成しましょう。