連載
プロフェッショナルVB.NETプログラミング
最終回 残されたいくつかのトピック(その3)
(株)ピーデー
川俣 晶
2003/01/18
|
|
Sharedコンストラクタ
クラスの中で、Sharedキーワードを付けたメンバは、インスタンスが作成されなくても存在し、インスタンスの数と関係なく実体は1つだけ存在する。このメンバを初期化するために、Sharedコンストラクタという機能がある。以下はそれを利用した例である。
1: Public Class A
2: Private Shared a(9) As String
3:
4: Shared Sub New()
5: Dim i As Integer
6: For i = 0 To 9
7: a(i) = "オフ"
8: Next
9: End Sub
10:
11: Public Shared Sub TurnOn(ByVal index As Integer)
12: a(index) = "オン"
13: End Sub
14:
15: Public Shared Sub Dump()
16: Dim i As Integer
17: For i = 0 To 9
18: Trace.WriteLine(a(i))
19: Next
20: End Sub
21: End Class
22:
23: Public Class Form1
24: Inherits System.Windows.Forms.Form
25:
26: …Windows フォーム デザイナで生成されたコード…
27:
28: Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
29: A.TurnOn(2)
30: A.TurnOn(5)
31: A.TurnOn(7)
32: A.Dump()
33: End Sub
34: End Class
|
|
Sharedなメンバを初期化するためのSharedコンストラクタを使用したサンプル・プログラム13 |
これを実行すると以下のようになる。
1: オフ
2: オフ
3: オン
4: オフ
5: オフ
6: オン
7: オフ
8: オン
9: オフ
10: オフ
|
|
サンプル・プログラム13の実行結果 |
このソースの中で、4〜9行目がSharedコンストラクタである。このSharedコンストラクタを呼び出すコードはどこにも記述されていない。しかし、Sharedなメンバを参照する前に、自動的にこのコンストラクタは呼び出される。Sharedなメンバを活用する場合には、便利な機能である。
配列の共変性
配列の共変性について、VB.NETの言語仕様では、以下のように記述されている。
『2つの参照型AとBで、AがBの派生型である場合、型Aから型Bの互換性のある配列への変換が存在します(互換性のある配列とは、ランクおよび型が同じ配列です)。この関係を“配列の共変性”と呼びます。』
書かれていることは難しいが、実例を見れば分かりやすいだろう。この特徴を使ったサンプル・プログラムを以下に示そう。
1: Public Class B
2: Public n As Integer
3: End Class
4:
5: Public Class A
6: Inherits B
7: End Class
8:
9: Public Class Form1
10: Inherits System.Windows.Forms.Form
11:
12: …Windows フォーム デザイナで生成されたコード…
13:
14: Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
15: Dim ar1(9) As A
16:
17: Dim i As Integer
18: For i = 0 To 9
19: ar1(i) = New A()
20: ar1(i).n = i
21: Next
22:
23: Dim ar2() As B
24: ar2 = ar1
25:
26: For i = 0 To 9
27: Trace.WriteLine(ar2(i).n)
28: Next
29: End Sub
30: End Class
|
|
配列の共変性により、配列を親クラスの配列として扱うサンプル・プログラム1 |
これを実行すると以下のようになる。
1: 0
2: 1
3: 2
4: 3
5: 4
6: 5
7: 6
8: 7
9: 8
10: 9
|
|
サンプル・プログラム1の実行結果 |
このソース・コードのポイントは、24行目で、クラスAの配列を、クラスBの配列を保持する変数に代入してしまっている点にある。これが可能であるのは、クラスAがクラスBを継承しているためである。クラスAはクラスBとして扱うこともできるので、クラスAの配列は、クラスBの配列として扱うこともできるわけである。
Disposeパターン
すでに述べたとおり、VB 6と異なり、VB.NETでは確保されたインスタンスが解放されるタイミングは決まっていない。ガベージコレクタが回収しに来た時点で、デストラクタが呼ばれ、資源が解放される。しかし、いつ来るか分からないガベージコレクタを待てない場合もある。資源を解放するタイミングを厳密に指定するために、IDisposableインターフェイスを使う方法がある。以下はIDisposableインターフェイスを実装した例である。
1: Public Class A
2: Implements IDisposable
3:
4: Public Sub New()
5: Trace.WriteLine("初期化")
6: End Sub
7:
8: Public Sub SomeProcess()
9: Trace.WriteLine("クラスを用いた何かの処理")
10: End Sub
11:
12: Sub Dispose() Implements IDisposable.Dispose
13: Trace.WriteLine("終了処理")
14: End Sub
15: End Class
16:
17: Public Class Form1
18: Inherits System.Windows.Forms.Form
19:
20: …Windows フォーム デザイナで生成されたコード…
21:
22: Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
23: Dim instance As New A()
24: Try
25: instance.SomeProcess()
26: Finally
27: instance.Dispose()
28: End Try
29: End Sub
30: End Class
|
|
IDisposableインターフェイスを実装したサンプル・プログラム1 |
これを実行すると以下のようになる。
1: 初期化
2: クラスを用いた何かの処理
3: 終了処理
|
|
サンプル・プログラム1の実行結果 |
IDisposableインターフェイスを使っていると、そのクラスがいったいどのような継承関係を持った何をするクラスかに関係なく、使い終わったらDisposeメソッドを呼び出せば正しく資源の解放が行われることが分かる。実際に、MSDNライブラリで“Dispose”というキーワードで検索すると、クラス・ライブラリの非常に多くのクラスが、このメソッドを実装していることが分かるだろう。興味のある方は、MSDN Libraryの「アンマネージ リソースをクリーンアップするためのFinalizeおよびDisposeの実装」というトピックを読むとよいだろう。
Insider.NET 記事ランキング
本日
月間