2012-01-06 51 views
2

我有一个叫做Modify的函数。它是这样挖掘的:处理泛型时在VB.Net中的多态性

Public Function Modify(Of SIMType As {New, DAOBase})(ByVal obj As DAOBase) As Boolean 

你可以看到这个函数是通用的。它将一个DAOBase或DAOBase的子类作为一个对象。

里面的修改功能有一个叫就像这样:

DAOToGP(obj) 

这就是多态性的用武之地。有四个左右的子类我创建了DAOBase。我已经为这些类型写了一个DAOToGP()。因此,在Modify()函数中,当它调用DAOToGP(obj)时,多态性应该启动,它应该调用DAOToGP()的正确实现,具体取决于我传递给Modify()的类型。

不过,我得到以下错误:

Error 20 Overload resolution failed because no accessible 'DAOToGP' can be called without a narrowing conversion: 
'Public Shared Function DAOToGP(distributor As Distributors) As Microsoft.Dynamics.GP.Vendor': Argument matching parameter 'distributor' narrows from 'SierraLib.DAOBase' to 'IMS.Distributors'. 
'Public Shared Function DAOToGP(product As Products) As Microsoft.Dynamics.GP.SalesItem': Argument matching parameter 'product' narrows from 'SierraLib.DAOBase' to 'IMS.Products'. C:\Users\dvargo.SIERRAWOWIRES\Documents\Visual Studio 2010\Projects\SIM\Dev_2\SIM\IMS\DVSIMLib\GP\GPSIMRunner\Runners\RunnerBase.vb 66 39 IMS 

我在这里的损失也有点。我不知道为什么它无法确定要调用哪个函数。有任何想法吗?

回答

1

您必须指定obj作为SIMType而不是DAOBase

Public Function Modify(Of SIMType As {New, DAOBase})(ByVal obj As SIMType) As Boolean 

否则,你的泛型类型参数将是无用的。


编辑:

你DAOToGP功能有不同的签名和显然不是从基类派生。试试这个:

Public Class DAOBase(Of Tin, Tout) 
    Public Function DAOToGP(ByVal obj As Tin) As Tout 
    End Function 
End Class 

Public Module Test_DAOBase 
    Public Function Modify(Of Tin, Tout)(ByVal obj As DAOBase(Of Tin, Tout)) As Boolean 
    End Function 
End Module 

你也可以声明DAOBAse为抽象类(为MustInherit)和DAOToGP作为一个抽象的函数(MustOverride):

Public MustInherit Class DAOBase(Of Tin As {New}, Tout) 
    Public MustOverride Function DAOToGP(ByVal obj As Tin) As Tout 
End Class 

Public Class DAOProduct 
    Inherits DAOBase(Of Products, SalesItem) 

    Public Overrides Function DAOToGP(ByVal obj As Products) As SalesItem 
     Return Nothing 
    End Function 
End Class 

Public Module Test_DAOBase 
    Public Function Modify(Of Tin As {New}, Tout)(ByVal obj As DAOBase(Of Tin, Tout)) As Boolean 
     Dim out As Tout = obj.DAOToGP(New Tin())  'This is OK 
    End Function 

    Public Sub TestModify() 
     Dim daoProd = New DAOProduct() 
     Modify(daoProd) 'This is OK 
    End Sub 
End Module 

然后声明不同类继承自DAOBase为参数类型的不同组合(在我的示例中为DAOProduct)。

+0

SIMTye在函数中使用了几个不同的地方。但为什么过载解析失败?为什么不能找到正确版本的'DAOToGP()'来使用 – user489041 2012-01-06 16:41:43

0

你要做的是根据参数的运行时类型在运行时执行重载解析。但VB的超载解决在编译时而不是运行时。 (除非您使用Option Strict Off,请参阅后面的内容。)

顺便说一句,这个问题与泛型的使用无关 - 在非泛型例程中它会一样。

这种少数类型的最佳解决方案可能是一个简单的If块。

If obj Is TypeOf subclassone Then 
    Dim obj1 As subclassone 
    obj1 = obj 
    DAOToGP(obj1) 
ElseIf obj Is TypeOf subclasstwo Then 
    Dim obj2 As subclasstwo 
    obj2 = obj 
    DAOToGP(obj2) 
    'and so on... 

或者你可以使用一个array of delegates indexed by System.Type在本similar question

另一种方法是使用Option Strict Off,然后写

Dim objWhatever As Object 
objWhatever = obj 
DAOToGP(obj) ' resolved at runtime, might Throw 

但我不建议这样做,因为禁用Option Strict Off看到一些很有用的编译器检查。