単にリソースを明示的に解放できるようにしたいならば、IDisposableインターフェイスを使わずともRelease
やClose
といった解放用のメソッドを用意しておき、それらのメソッドを呼び出すようにすることもできます。 しかし、IDisposableを実装しておくと、usingステートメントによる構文の補助に基づく確実な解放処理が行えるようになります。 加えて、IDisposableインターフェイスによって、型が解放されるべきリソースを保持していることを表明できます。
Dispose
以外のメソッド名で解放処理を提供したいといった場合には、次の例のように別名の解放用メソッドを公開しつつ、IDisposable.Disposeメソッドは明示的に実装(またはPrivate
として実装)し、それを呼び出すようにすることができます。 このようにすることでDispose
以外のメソッド名で解放処理を提供できると同時に、IDisposableインターフェイスによる解放処理も提供できます。
IDisposableインターフェイスを実装し、Dispose以外のメソッド名で解放処理を公開する
Imports System
Imports System.Runtime.InteropServices
Class UnmanagedMemory
Implements IDisposable
Public Ptr As IntPtr ' アンマネージメモリ領域を参照するポインタ
Public Sub New(ByVal size As Integer)
' メモリ領域を確保する
Ptr = Marshal.AllocHGlobal(size)
End Sub
' メモリ領域を確保するためのメソッドとして、Disposeではない別名のメソッドを提供する
' (IDisposable.DisposeをPrivateな実装にし、それを呼び出すようにする)
Public Sub Free()
DirectCast(Me, IDisposable).Dispose()
End Sub
' PrivateなIDisposable.Disposeの実装
Private Sub Dispose() Implements IDisposable.Dispose
If Ptr = IntPtr.Zero Then Return
Marshal.FreeHGlobal(Ptr)
Ptr = IntPtr.Zero
End Sub
End Class
Class Sample
Shared Sub Main()
' IDisposableインターフェイスを実装するオブジェクトを作成する
' (本来ならUsingステートメントを使ったほうがよいが、例示のため省略)
Dim mem As New UnmanagedMemory(4)
Marshal.WriteInt32(mem.Ptr, 16)
' Freeメソッドでアンマネージリソースを解放する
' (このメソッド経由でIDisposable.Disposeメソッドが呼び出される)
mem.Free()
End Sub
End Class