非同期プログラミングの概要

IAsyncResult デザイン パターンを使用する非同期操作は、BeginOperationName および EndOperationName という名前の 2 つのメソッドとして実装されます。これらは、非同期操作 OperationName をそれぞれ開始および終了するものです。 たとえば、FileStream クラスは、BeginRead および EndRead メソッドを提供して、非同期的にファイルからバイトを読み取ります。 これらのメソッドは、非同期バージョンの Read メソッドを実装します。

BeginOperationName を呼び出した後、アプリケーションは、別のスレッドで非同期操作が行われている間も、呼び出し元スレッドで命令の実行を続行できます。 BeginOperationName を呼び出すたびに、アプリケーションは EndOperationName も呼び出して、操作の結果を取得する必要があります。

非同期操作の開始

BeginOperationName メソッドは、非同期操作 OperationName を開始し、IAsyncResult インターフェイスを実装するオブジェクトを返します。 IAsyncResult オブジェクトは、非同期操作に関する情報を格納します。 非同期操作に関する情報を次の表に示します。

メンバー

説明

AsyncState

オプションのアプリケーション固有のオブジェクト。非同期操作に関する情報を含みます。

AsyncWaitHandle

WaitHandle。非同期操作が完了するまで、アプリケーションの実行をブロックするのに使用できます。

CompletedSynchronously

別の ThreadPool スレッドで完了したかどうかではなく、BeginOperationName の呼び出しに使用されたスレッドで非同期操作が完了したかどうかを示す値。

IsCompleted

非同期操作が完了したかどうかを示す値。

BeginOperationName メソッドは、同期バージョンのメソッドのシグネチャで宣言されたパラメーターのうち、値渡しまたは参照渡しのパラメーターをすべて受け取ります。 out パラメーターは、BeginOperationName メソッド シグネチャの一部にはなりません。 BeginOperationName メソッド シグネチャには、2 つの追加のパラメーターも含まれます。 1 つ目のパラメーターは、非同期操作が完了したときに呼び出されるメソッドを参照する AsyncCallback デリゲートを定義します。 操作完了時にメソッドを呼び出さない場合、呼び出し元は null (Visual Basic では Nothing) を指定できます。 2 つ目の追加のパラメーターは、ユーザー定義オブジェクトです。 このオブジェクトは、アプリケーション固有の状態情報を、を使用すると、非同期操作が完了したときに呼び出されるメソッドに渡すために使用できます。 ファイルから読み取ったバイトを格納するバイト配列など、操作固有の追加のパラメーターを BeginOperationName メソッドが受け取る場合は、AsyncCallback とアプリケーション状態オブジェクトが BeginOperationName メソッド シグネチャの最後のパラメーターになります。

BeginOperationName は、呼び出し元スレッドに即座に制御を戻します。 BeginOperationName メソッドが例外をスローする場合、例外は非同期操作が開始される前にスローされます。 BeginOperationName メソッドが例外をスローすると、コールバック メソッドは呼び出されません。

非同期操作の終了

EndOperationName メソッドは、非同期操作 OperationName を終了します。 EndOperationName メソッドの戻り値は、対応する同期操作で返されるものと同じ型であり、非同期操作に固有の値になります。 たとえば、EndRead メソッドは FileStream から読み取ったバイト数を返し、EndGetHostByName メソッドはホスト コンピューターに関する情報を含む IPHostEntry オブジェクトを返します。 EndOperationName メソッドは、同期バージョンのメソッドのシグネチャで宣言されたパラメーターのうち、out パラメーターと ref パラメーターをすべて受け取ります。 EndOperationName メソッドは、同期メソッドのパラメーターに加えて、IAsyncResult パラメーターも受け取ります。 呼び出し元は、対応する BeginOperationName の呼び出しから返されたインスタンスを渡す必要があります。

IAsyncResult オブジェクトによって表される非同期操作が EndOperationName の呼び出し時にまだ完了していない場合、EndOperationName は、非同期操作が完了するまで呼び出し元スレッドをブロックします。 非同期操作によってスローされた例外は、EndOperationName メソッドからスローされます。 同じ IAsyncResult を使用して EndOperationName メソッドを複数回呼び出した場合の結果は定義されていません。 同様に、関連する Begin メソッドによって返されたのではない IAsyncResult を使用して EndOperationName メソッドを呼び出した場合の動作も定義されていません。

メモメモ

実装側では、このような未定義のシナリオに対して InvalidOperationException をスローすることを検討してください。

メモメモ

このデザイン パターンの実装側は、非同期操作の完了を呼び出し元に通知する必要があります。そのためには、IsCompleted を true に設定し、非同期コールバックが指定されている場合はそれを呼び出し、AsyncWaitHandle をシグナル状態にします。

アプリケーション開発者には、非同期操作の結果にアクセスするためのデザインとして、いくつかの選択肢があります。 適切な選択は、操作の完了前に実行できる命令がアプリケーションにあるかどうかによって異なります。 アプリケーションが非同期操作の結果を受け取るまで他の作業を実行できない場合は、結果が使用可能になるまで、そのアプリケーションをブロックする必要があります。 非同期操作が完了するまでブロックするには、次のいずれかの方法を使用します。

非同期操作が完了するまでアプリケーションをブロックする必要がない場合は、次のいずれかの方法を使用します。

参照

概念

同期メソッドの非同期呼び出し

AsyncCallback デリゲートおよび状態オブジェクトの使用

その他の技術情報

非同期プログラミングのデザイン パターン