世界の国564520 views
ヒストリア290598 views
高校物理160203 views
教育149510 views
高校国語788336 views
いろは3010814 views
高校化学2924392 views
Computer368106 views
高校生物551766 views
数学講師2886227 views
Help
Tools
NewsSpreadsheetCalendarSlidesTier ListPen ToolIllustrationCrayonPixel ArtASCII ArtPerspectiveEndless StairsGraphMind MapER DiagramFamily TreeMemeCurved TextImage EditorMosaicRetro FilterPencil SketchOCR/HighlighterMakeup EditorFaviconVideo TrimmerScrolling VideoVideo TitleColor PickerColor ExtractorBonfireFireworksWater RippleWater SplashBreaking GlassWood GrainMarble TextureCSS ButtonIcon MakerBar ChartGrouped Bar ChartStacked Bar ChartPie ChartLine ChartArea ChartStacked Area ChartScatter Plot3D Bar Chart3D Pie ChartBar Chart RaceBubble ChartPopulation PyramidPictogramEarningsCandlestick ChartInvestment RiskMortgage SimulatorCalculatorMatrix CalculatorFunction GraphPolynomial ExpansionVenn DiagramField VisualizerRubik's Cube Group TheoryTraveling SalesmanVoronoi and DelaunayFractalColumn ArithmeticDraw Math FiguresArithmetic AnimationArithmetic Word ProblemsCounting with Tree DiagramsCube NetsCross SectionsMotion PathMechanicsWavesLight and LensesThermodynamicsHow Semiconductors WorkMolecular StructuresAtomic OrbitalsElectrochemical CellsChemical EquilibriumCrystal LatticesBuffer pHComplex IonsDNA Double HelixCell DivisionMembrane ChannelsNerve ImpulseRock ClassificationWeatherConstellationsSolar and Lunar Eclipses3D ModelingFloor PlanSeismic StructuresIntersection TurnMaglevCooking AnimationOrigamiLive Viewer CountGeoJSON MapRailway MapPopulation MapCrime MapLand Price MapSchool MapShrine and Castle MapHouse of Representatives MapWord MapSolitaireReversiHakoiri MusumeChessHamburgerRippleSlide Puzzle MakerNeon PinballNovel MakerJapanese Typing PracticePiano Score EditorMusic Theory

English

Python の非同期コンテキストマネージャ

Python の非同期プログラミング(asyncio)では、async with 構文を使って非同期コンテキストマネージャを扱います。非同期のリソース管理やセットアップ・クリーンアップ処理に必要です。

非同期コンテキストマネージャとは

通常の with 文は同期的な __enter__()__exit__() を呼び出しますが、async with は非同期版の __aenter__()__aexit__() を呼び出します。

同期(with)

enter() と exit() を使用。通常の関数。

非同期(async with)

aenter() と aexit() を使用。コルーチン(async def)。

クラスベースの実装

非同期コンテキストマネージャをクラスで実装する例です。

import asyncio

class AsyncConnection:
    def __init__(self, host):
        self.host = host
    
    async def __aenter__(self):
        print(f"{self.host} に接続中...")
        await asyncio.sleep(1)  # 接続をシミュレート
        print("接続完了")
        return self
    
    async def __aexit__(self, exc_type, exc_val, exc_tb):
        print("切断中...")
        await asyncio.sleep(0.5)  # 切断をシミュレート
        print("切断完了")
    
    async def fetch(self, path):
        await asyncio.sleep(0.5)
        return f"Data from {self.host}{path}"

async def main():
    async with AsyncConnection("example.com") as conn:
        data = await conn.fetch("/api/data")
        print(data)

asyncio.run(main())

@asynccontextmanager デコレータ

contextlib.asynccontextmanager を使うと、非同期ジェネレータから簡単に作成できます。

import asyncio
from contextlib import asynccontextmanager

@asynccontextmanager
async def async_timer(label):
    start = asyncio.get_event_loop().time()
    print(f"{label} 開始")
    yield
    elapsed = asyncio.get_event_loop().time() - start
    print(f"{label} 完了: {elapsed:.2f}秒")

async def main():
    async with async_timer("データ取得"):
        await asyncio.sleep(1)

asyncio.run(main())

aiofiles での非同期ファイル操作

aiofiles ライブラリは非同期ファイル I/O を提供し、async with で使えます。

import asyncio
import aiofiles

async def write_file():
    async with aiofiles.open("output.txt", "w") as f:
        await f.write("非同期で書き込み")

async def read_file():
    async with aiofiles.open("output.txt", "r") as f:
        content = await f.read()
        print(content)

async def main():
    await write_file()
    await read_file()

asyncio.run(main())

aiohttp での HTTP クライアント

aiohttp は非同期 HTTP クライアントを提供します。

import asyncio
import aiohttp

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

async def main():
    html = await fetch_url("https://example.com")
    print(f"取得: {len(html)} 文字")

asyncio.run(main())

セッションとレスポンスの両方が非同期コンテキストマネージャです。

asyncio.Lock

非同期ロックも async with で使えます。

import asyncio

lock = asyncio.Lock()

async def critical_section(name):
    async with lock:
        print(f"{name} がロック取得")
        await asyncio.sleep(1)
        print(f"{name} がロック解放")

async def main():
    await asyncio.gather(
        critical_section("タスクA"),
        critical_section("タスクB"),
    )

asyncio.run(main())

AsyncExitStack

動的な非同期リソース管理には AsyncExitStack を使います。

import asyncio
from contextlib import AsyncExitStack

@asynccontextmanager
async def resource(name):
    print(f"{name} 確保")
    yield name
    print(f"{name} 解放")

async def main():
    async with AsyncExitStack() as stack:
        r1 = await stack.enter_async_context(resource("A"))
        r2 = await stack.enter_async_context(resource("B"))
        print(f"使用中: {r1}, {r2}")

asyncio.run(main())

非同期プログラミングでは、ネットワーク接続やファイル I/O などの I/O バウンドな処理が多くなります。async with を使うことで、これらのリソースを安全に管理できます。