将List(Of ChildClass)作为参数传递给期望List(Of ParentClass)的方法?

时间:2010-04-12 09:30:35

标签: vb.net inheritance list .net-2.0 parameter-passing

我已经为两个名为字段的父类实现了继承。每个父类都有几个子类。在父类中,我创建了一个期望参数列表(字段)的方法。

尝试将参数 List(Of ChildField)传递给期望参数 List(Of Field)的方法时出错。错误消息如下:

  

类型的价值   “System.Collections.Generic.List(中   com.hlb.icisbatch.data.ChildField)“
  无法转换为   “System.Collections.Generic.List(中   com.hlb.icisbatch.data.Field)'

我的问题,是否可以将子类列表作为参数传递?如果它不是一个列表,那么它工作正常。但不知何故,列表无法实现?

以下是示例类结构:

    Table              Field
      |                  |
  ChildTable         ChildField

我在父类中有一个方法:

Public Class Table

    Public Sub New()
    End Sub

    Public Overridable Sub setFields(ByVal list As List(Of Field)
       'Do work here'
    End Sub

 End Class
子类中的

和方法:

Public Class ChildTable

    Public Sub New(ByVal list As List(Of ChildField)
       setFields(ChildField)
    End Sub

 End Class

2 个答案:

答案 0 :(得分:1)

不,这是不可能的 - 而且有充分的理由。考虑如果调用代码试图将Field(或其他某些派生类)的实例添加到列表中会发生什么。不好的事情会发生。

在.NET 4(可能是VB10)中,这可以通过通用委托和接口(而不是类)的协方差和逆变来实现 - 但只能在安全的地方。因此IList(Of T) 不是变体(因为值在API的“in”和“out”中); IEnumerable(Of T)是协变的(因此从IEnumerable(Of String)转换为IEnumerable(Of Object))并且IComparer(Of T)是逆变的(因此从IComparer(Of Object)转换为IComparer(Of String)例如)。

(从v2.0开始,这种能力实际上已经在CLR中,但它只出现在.NET 4的语言和框架中。)

答案 1 :(得分:0)

因此,对于.Net 4.0+(可能也是早期版本),您必须更改setFields方法:

Public Overridable Sub setFields(As T Of Field)(ByVal list As List(Of T)
   'Do work here'
End Sub

然后当你用:

打电话时
Public Sub New(ByVal list As List(Of ChildField)
   setFields(list)
End Sub

它本质上是在呼唤:

setFields(Of ChildField)(list)

这意味着setFields知道它正在处理一个ChildField对象列表,并且不会让任何人做任何顽皮的事情,比如添加一个不同的ChildNumber2Field对象。

尽管.Net 2.0中引入了泛型,但我不确定该版本究竟是多么先进。