
拡張メソッド、インスタンス メソッド、およびプロパティ
スコープ内のインスタンス メソッドが、呼び出し元ステートメントの引数と互換性があるシグネチャを持っている場合、拡張メソッドよりもそのインスタンス メソッドの方が優先的に使用されます。この場合、より適合する拡張メソッドがあっても、インスタンス メソッドの方が優先されます。次の例では、ExampleClass に、Integer 型のパラメータを 1 つ持つ ExampleMethod という名前のインスタンス メソッドが含まれています。拡張メソッド ExampleMethod は ExampleClass を拡張し、Long 型のパラメータを 1 つ持ちます。
Class ExampleClass
' Define an instance method named ExampleMethod.
Public Sub ExampleMethod(ByVal m As Integer)
Console.WriteLine("Instance method")
End Sub
End Class
<Extension()> _
Sub ExampleMethod(ByVal ec As ExampleClass, _
ByVal n As Long)
Console.WriteLine("Extension method")
End Sub
次のコードでは、ExampleMethod の最初の呼び出しで、拡張メソッドが呼び出されます。これは、arg1 が Long であり、拡張メソッドの Long パラメータとのみ互換性があるためです。ExampleMethod の 2 回目の呼び出しでは、Integer 引数 arg2 があるため、インスタンス メソッドが呼び出されます。
Sub Main()
Dim example As New ExampleClass
Dim arg1 As Long = 10
Dim arg2 As Integer = 5
' The following statement calls the extension method.
example.ExampleMethod(arg1)
' The following statement calls the instance method.
example.ExampleMethod(arg2)
End Sub
次は、2 つのメソッド間でパラメータのデータ型が逆になっています。
Class ExampleClass
' Define an instance method named ExampleMethod.
Public Sub ExampleMethod(ByVal m As Long)
Console.WriteLine("Instance method")
End Sub
End Class
<Extension()> _
Sub ExampleMethod(ByVal ec As ExampleClass, _
ByVal n As Integer)
Console.WriteLine("Extension method")
End Sub
今回は、Main 内のコードはどちらの場合でもインスタンス メソッドを呼び出します。これは、arg1 と arg2 は Long へ拡大変換され、どちらの場合でも拡張メソッドよりインスタンス メソッドの方が優先されるためです。
Sub Main()
Dim example As New ExampleClass
Dim arg1 As Long = 10
Dim arg2 As Integer = 5
' The following statement calls the instance method.
example.ExampleMethod(arg1)
' The following statement calls the instance method.
example.ExampleMethod(arg2)
End Sub
つまり、既存のインスタンス メソッドの代わりに拡張メソッドを使用することはできません。一方、拡張メソッドとインスタンス メソッドの名前が同じでもシグネチャが競合しない場合は、両方のメソッドを使用できます。たとえば、クラス ExampleClass に引数を使用しない ExampleMethod という名前のメソッドがあるとします。拡張メソッドの名前がそのメソッドと同じでもシグネチャが違えば、その拡張メソッドを使用することは可能です。次に例を示します。
Imports ConsoleApplication2.ExtensionExample
Module Module1
Sub Main()
Dim ex As New ExampleClass
' The following statement calls the extension method.
ex.ExampleMethod("Extension method")
' The following statement calls the instance method.
ex.ExampleMethod()
End Sub
Class ExampleClass
' Define an instance method named ExampleMethod.
Public Sub ExampleMethod()
Console.WriteLine("Instance method")
End Sub
End Class
End Module
Imports System.Runtime.CompilerServices
' Define an extension method named ExampleMethod.
Module ExtensionExample
<Extension()> _
Sub ExampleMethod(ByVal ec As ExampleClass, _
ByVal stringParameter As String)
Console.WriteLine(stringParameter)
End Sub
End Module
このコードの出力は次のようになります。
Extension method
Instance method
プロパティの場合、状況はより単純です。拡張メソッドの名前がそのクラスのプロパティと同じである場合、その拡張メソッドは非表示になり、アクセスできません。