.NET Framework で、IDisposable インターフェイスを実装したクラスのインスタンスは、使用後に Dispose メソッドを呼び出す必要があります。ところが、呼び出すタイミングに注意が必要な場合があります。
System.IO.StreamReader クラスは、System.IO.TextReader クラスを継承しています。TextReader クラスは IDisposable インターフェイスを実装しているので、Dispose メソッドを実装しています。ただし、Dispose メソッドは明示実装により隠蔽されており、Close メソッドが代替メソッドとして用意されています。
StreamReader クラスのコンストラクタは、いくつかのオーバーロードがあります。そのうちのひとつに、System.IO.Stream クラスのインスタンスを引数にするものがあります。このコンストラクタを使用する場合、Close メソッドの呼び出しには注意が必要です。
IDisposable インターフェイスは、そのクラスがアンマネージドリソースを使用することを、開発者に知らせます。StreamReader クラスにおけるアンマネージドリソースは、ファイル名を指定した場合はファイルハンドル、ストリームを指定した場合はストリームです。
この辺でピン!と来ましたか?ストリームを引数にして生成したインスタンスで Close メソッドをコールすると、元にしたストリームの Close メソッドもコールされます。。。FileStream を、リード/ライトで開いて、TextReader で読み込み、リワインドして TextWriter で上書き……なんて処理をするとき、TextReader.Close は、TextWriter.Close をするときまで呼び出してはいけません。元にしたストリームが閉じてしまいます。
TextWriter.Close メソッドが破棄するものがストリームしかなければ、TextWriter.Close メソッドをコールする必要もありませんが、私は ildasm を通して見るようなことはしていませんし、「何でこれはしないの?」と、後から混乱する元になるので、「しなくてもいい」とは言いません。
投稿日時 : 2006年2月11日 10:24