我正试图找出这种奇怪的行为。我有一个基类(A),带有一个名为“M”的重载方法:一个用于整数,一个用于浮点数(单个用于VB.NET)。
另一方面,我有一个继承自A的第二个类(B),它以两种方式重载方法M:一个用于数据类型double,一个用于对象数据类型。
问题是:我希望方法将每个函数用于其数据类型,但由于某些奇怪的原因,具有Object数据类型的方法接受所有调用。为什么会这样?
我希望这个程序的输出为15
,而是4
。
这是代码(VB.NET):
Module Module1
Public Class A
Public Function M(ByVal a As Integer) As Integer
Return 8
End Function
Public Function M(ByVal a As Single) As Integer
Return 4
End Function
End Class
Public Class B
Inherits A
Public Overloads Function M(ByVal a As Double) As Integer
Return 2
End Function
Public Overloads Function M(ByVal a As Object) As Integer
Return 1
End Function
End Class
Sub Main()
Dim a0 As Double = 1
Dim a1 As Single = 2
Dim a2 As Integer = 4
Dim a3 As Object = 8
Dim arre(4)
arre(0) = a0
arre(1) = a1
arre(2) = a2
arre(3) = a3
Dim b As New B
Dim suma% = 0
For i = 0 To 3
suma += b.M(arre(i))
Next i
Console.WriteLine(suma)
System.Threading.Thread.CurrentThread.Sleep(2000)
End Sub
End Module
答案 0 :(得分:1)
它调用带Object
的重载的原因是因为您的数组类型为Object
。
' original code
Dim arre(4)
arre(0) = a0
arre(1) = a1
arre(2) = a2
arre(3) = a3
' verbose version
Dim arre(4) As Object
arre(0) = DirectCast(a0, Object)
arre(1) = DirectCast(a1, Object)
arre(2) = DirectCast(a2, Object)
arre(3) = DirectCast(a3, Object)
在.NET中查找“装箱”和“拆箱”,有大量优秀的文章可以更详细地解释这一点。
答案 1 :(得分:0)
每次都会在示例中调用Object重载,因为您将数组声明为Object数组。 (Option Strict
会强制你把As Object
放在它之后,但这不会改变事情。)你放入数组的类型并不重要,因为这些值被“装箱”到了对象中
考虑以下内容,简化以演示正在发生的事情 (您不需要自定义类或继承来演示您所看到的内容)
Module Module1
Public Function M(ByVal a As Integer) As Integer
Return 8
End Function
Public Function M(ByVal a As Object) As Integer
Return 1
End Function
Sub Main()
Dim a0 As Integer = 0
Dim a1 As Object = 0
Dim arre(1)
arre(0) = a0
arre(1) = a1
Console.WriteLine(M(arre(0)))
' 1, arre() is implicitly typed as an array of Objects
' so the Object overload will be called
Console.WriteLine(M(arre(1)))
' 1, see above
Console.WriteLine(M(DirectCast(arre(0), Integer)))
' 8, explicit cast to an Integer
Console.WriteLine(M(DirectCast(arre(1), Integer)))
' 8, see above
Console.WriteLine(M(a0))
' 8, a0 declared explicitly as an Integer
Console.WriteLine(M(a1))
' 1, a1 declared explicitly as an Object
Threading.Thread.Sleep(2000)
End Sub
End Module