リソース管理の概要
リソースという用語は、文脈によってさまざまな意味をもっています。例えば、文脈によって「文字列」を指したり、「画像データ」を指したりします。今回のトピックでの「リソース」は、グラフィックデバイスコンテキスト・ファイルハンドル・ネットワークおよびDB接続・同時実行中の待機ハンドルオブジェクトなどの、ソフトウェアまたはOSリソースのことを指します。
アプリケーションによるこれらのリソース使用には、OSや他のリソースプロバイダからの「リソース取得」と、リソースプールへの「リソース解放」が必要となります。リソース解放をすることで別のアプリケーションが改めてそのリソースを利用できるようになるため、アプリケーションがリソースをリソースプールに解放しないと問題が発生します。
リソース管理
アプリケーション内のリソースを効率的かつ責任をもって管理するには、迅速かつ予測可能な方法でリソースを解放する必要があります。.NETでは、System.IDisposableインターフェースを提供することでこれを実現しています。System.IDisposableインターフェースを実装する型には、リソースを正しく解放するためのSystem.IDisposable.Dispose()メソッドが定義されます。これが正しく実装されているアプリケーションは、保持しているリソースが不要となった時点で解放処理がすぐに呼び出されることが保証されています。F#では、Disposeパターンをサポートするために「use束縛(= useバインディング)」と「using関数」という2種類の構文が用意されています。サンプルでみるリソース管理
use束縛
useキーワードによるバインディングは、let束縛とよく似ています。実際に、use束縛はlet束縛と同等の機能を提供しています。さらにlet束縛とは違い、値がスコープ範囲外になったとき、Dispose()メソッドを呼び出す機能が備わっています。また、Dispose()メソッドを呼び出す前にコンパイラは値のnullチェックを実施するため、値がnullの場合はDispose()メソッドの呼び出しを行わないようになっています。次の例は、use束縛を使用してファイルリソースを自動的に解放する方法を示しています。
using関数
using関数は「リソースを引数に取る関数」をパラメータとして受け取る高階関数です。using関数内でのみリソースは有効で、using関数の処理が完了すると同時にリソースは解放されます。次の例は、using関数を使用してファイルリソースを自動的に解放する方法を示しています。
use束縛とusing関数は、リソースの有効である範囲が違う以外は基本的に同等の機能を提供しています。一般的にusing関数ではなく、use束縛を利用することが推奨されていますが、スコープの違いが重要な状況などでは、しっかりと使い分けをするようにしましょう。