連載

プロフェッショナルVB.NETプログラミング
―― VB 6プログラマーのためのVB.NET入門 ――

最終回 残されたいくつかのトピック(その3)

(株)ピーデー
川俣 晶
2003/01/18

Page1 Page2 Page3

オーバーロード

 VB 6(Visual Basic 6.0)では、同じ名前のメソッドを同じコンテキスト内で複数記述するとエラーが起きた。以下はVB 6でエラーになるサンプル・プログラムである。引数の型や数が異なるTwoTimesというメソッドが3つ定義されているが、同じフォーム・モジュール中に同じ名前のメソッドが複数あるとエラーになる。

  1: Private Sub TwoTimes(ByVal n As Integer)
  2:   Debug.Print n * 2
  3: End Sub
  4:
  5: Private Sub TwoTimes(ByVal n1 As Integer, ByVal n2 As Integer)
  6:   Debug.Print (n1 + n2) * 2
  7: End Sub
  8:
  9: Private Sub TwoTimes(ByVal s As String)
 10:   Debug.Print s & s
 11: End Sub
 12:
 13: Private Sub Form_Load()
 14:   TwoTimes 123
 15:   TwoTimes 123, 456
 16:   TwoTimes "123"
 17: End Sub
引数の型や数が異なる同名のメソッドを定義したVB 6のサンプル・プログラム1(コンパイル・エラーとなる)

 しかし、これをそのままVB.NET(Visual Basic .NET)用に書き換えると、これは動作する。

  1: Private Sub TwoTimes(ByVal n As Integer)
  2:   Trace.WriteLine(n * 2)
  3: End Sub
  4:
  5: Private Sub TwoTimes(ByVal n1 As Integer, ByVal n2 As Integer)
  6:   Trace.WriteLine((n1 + n2) * 2)
  7: End Sub
  8:
  9: Private Sub TwoTimes(ByVal s As String)
 10:   Trace.WriteLine(s & s)
 11: End Sub
 12:
 13: Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
 14:   TwoTimes(123)
 15:   TwoTimes(123, 456)
 16:   TwoTimes("123")
 17: End Sub
サンプル・プログラムをVB.NET用に書き換えたのサンプル・プログラム2

 これを実行すると以下のようになる。

 1: 246
 2: 1158
 3: 123123
サンプル・プログラム2の実行結果

 このように、引数の型や種類が異なる同じ名前のメソッドを宣言することをオーバーロードという。VB.NETでは、オーバーロードが可能となっている。VB 6ではデータは何でもとりあえずVariant型で受けて処理するという方法が使えたので、オーバーロードの必要性は薄かったかもしれない。だが、VB.NETでデータ型を厳密に扱うプログラミングを行うようになると、必須となる機能といえる。同じ名前のメソッドでも、データ型を細かく分けて別々のメソッドとして処理するプログラミングをするようになれば、避けては通れない機能である。

 なお、以下の要素が異なっていても、異なるメソッドとは認識されない。

  • 型メンバの修飾子(SharedやPrivateなど)
  • パラメータの修飾子(ByVal や ByRefなど)
  • パラメータの名前
  • メソッドの戻り値の型
  • プロパティの要素型

 オーバーロードは、メソッドだけでなく、コンストラクタやプロパティでも使用できる。

Protectedアクセス

 メソッドなどには、PrivateやPublicといったキーワードを付けて、それにアクセスできる範囲をコントロールすることができる。ソース・コードの意図しない行から呼び出されないために、このようなキーワードを正しく使うことは、ソフトウェアの品質を上げるために重要な意味がある。この連載のサンプル・プログラムの中にも、分かりやすさのためにPublicとしているが本当はPublicにすべきではないケースも含まれる。それはさておき、VB 6にはなかった新しいキーワードProtectedがVB.NETには存在している。これは、継承を行った場合に意味がある機能を割り当てられたもので、継承がないVB 6にないのは当然といえる機能である。以下に、Protectedを使用したサンプル・プログラムを示す。

  1: Public Class A
  2:   Protected Sub Sample1()
  3:     Trace.WriteLine("クラスAのSample1が呼ばれました")
  4:   End Sub
  5:   Public Sub Sample2()
  6:     Sample1()
  7:   End Sub
  8: End Class
  9:
 10: Public Class B
 11:   Inherits A
 12:   Public Sub Sample3()
 13:     Sample1()
 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 instanceA As New A()
 24:     Dim instanceB As New B()
 25:     'instanceA.Sample1()
 26:     instanceA.Sample2()
 27:     'instanceB.Sample1()
 28:     instanceB.Sample2()
 29:     instanceB.Sample3()
 30:   End Sub
 31: End Class
Protectedキーワードを使用したサンプル・プログラム3

 これを実行すると以下のようになる。

 1: クラスAのSample1が呼ばれました
 2: クラスAのSample1が呼ばれました
 3: クラスAのSample1が呼ばれました
サンプル・プログラム3の実行結果

 Publicキーワードはどこからでも呼び出せることを指定し、Privateキーワードは同じクラス内からのみ呼び出せることを指定する。それに対して、Protectedキーワードは、同じクラスと、そのクラスを継承したクラスからのみ呼び出せることを指定する。そのため、6行目のように、同じクラスからの呼び出しは実現できる。また、13行目のように、クラスAを継承したクラスBからも呼び出すことができる。しかし、継承関係のないForm1クラス内からは呼び出せず、25行目や27行目の行からシングルクォートを取り除いて有効にすると、ビルド・エラーになる。Protectedは継承を多用する場合に便利な機能であり、知っておく価値がある。

継承を禁止するNotInheritableキーワード

 クラスを宣言する際に、必ず継承しなければならないことを示すMustInheritキーワードについてはすでに解説した。このほかに逆の効能を持つキーワード、NotInheritableがある。以下のサンプル・プログラムは、それを使用した例である。

 1: Public NotInheritable Class A
 2:   Private a As Integer
 3: End Class
 4:
 5: Public Class B
 6:   Inherits A
 7:   Private b As Integer
 8: End Class
継承を禁止するNotInheritableキーワードを使用したサンプル・プログラム12(コンパイル・エラーとなる)

 このように記述すると、ビルド時にエラーになる。1行目でクラスAには、NotInheritableキーワードが付いているので、クラスAを継承することは出来ない。6行目で、クラスAを継承しようとしているが、これはエラーになる。内部の実装にトリックを使ったりして、継承すると不都合が起きるようなクラスを作った場合は、このキーワードを付けておくと、誤って継承してもエラーが起きて気付くことができる。


 INDEX
  連載 プロフェッショナルVB.NETプログラミング
  最終回 残されたいくつかのトピック(その3)
  1.オーバーロード/Protectedアクセス/継承を禁止するNotInheritable
    2.Sharedコンストラクタ/配列の共変性/Disposeパターン
    3.クラス・ライブラリの概要
 
「プロフェッショナルVB.NETプログラミング」


Insider.NET フォーラム 新着記事
  • 第2回 簡潔なコーディングのために (2017/7/26)
     ラムダ式で記述できるメンバの増加、throw式、out変数、タプルなど、C# 7には以前よりもコードを簡潔に記述できるような機能が導入されている
  • 第1回 Visual Studio Codeデバッグの基礎知識 (2017/7/21)
     Node.jsプログラムをデバッグしながら、Visual Studio Codeに統合されているデバッグ機能の基本の「キ」をマスターしよう
  • 第1回 明瞭なコーディングのために (2017/7/19)
     C# 7で追加された新機能の中から、「数値リテラル構文の改善」と「ローカル関数」を紹介する。これらは分かりやすいコードを記述するのに使える
  • Presentation Translator (2017/7/18)
     Presentation TranslatorはPowerPoint用のアドイン。プレゼンテーション時の字幕の付加や、多言語での質疑応答、スライドの翻訳を行える
@ITメールマガジン 新着情報やスタッフのコラムがメールで届きます(無料)

注目のテーマ

Insider.NET 記事ランキング

本日 月間