Vb.net 子接口';s Load(x)函数隐藏父接口';s Load()函数

Vb.net 子接口';s Load(x)函数隐藏父接口';s Load()函数,vb.net,inheritance,interface,Vb.net,Inheritance,Interface,我有以下通用接口 Public Interface IGenericDAO(Of T As {Class, IEntity}) Sub Save(entity As T) Sub Delete(entity As T) Sub Delete(id As Long) Function Load(id As Long) As T Function Load() As List(Of T) End Interface 我想要另一个像这样的 Publ

我有以下通用接口

Public Interface IGenericDAO(Of T As {Class, IEntity})

    Sub Save(entity As T)

    Sub Delete(entity As T)

    Sub Delete(id As Long)

    Function Load(id As Long) As T

    Function Load() As List(Of T)

End Interface
我想要另一个像这样的

Public Interface IAgendaDAO
    Inherits IGenericDAO(Of Agenda)

    Function Load(isPublished As Boolean, meetingType As MeetingType) As List(Of Agenda)

    Function Load(meetingType As Boolean) As List(Of Agenda)

End Interface
但在本例中,编译器说我的加载函数隐藏了没有参数的加载函数 我可以在C#中做这样的事情,为什么我不能在VB.NET中做呢?
我能做些什么来解决这个问题?我应该为每个函数分别命名吗

是的,这是语言设计师需要做出的基本选择之一。核心决策是当派生类的成员与基类中的成员具有完全相同的名称时应该发生什么。这会隐藏继承的基类成员,并使基类成员难以使用。这是有风险的,一个无辜的维护更改可能会突然不再隐藏基本成员并破坏现有代码

C#语言设计师选择了“签名隐藏”。换句话说,仅当基本方法具有完全相同的名称和参数时,方法才会隐藏。这是您在这些接口声明中习惯并希望发生的事情

其他语言,如C++和VB.NET,都是为了“名藏”。换句话说,当一个方法具有相同的名称时,不管它使用什么参数,它都会隐藏。这是一个“不太令人惊讶”的选择,它更容易推理,并且维护更改不太可能改变现有代码的行为

您可以在以下示例代码中看到这一点:

Class Base
    Sub foo()
    End Sub
End Class

Class Derived
    Inherits Base

    Sub foo(i As Integer)   '' Warning: 'foo' shadows an overloadable member declared in Base
    End Sub

    Shadows Sub foo(d As Double)   '' No warning, Shadows suppresses it
    End Sub
End Class

Sub Main()
    Dim obj = New Derived
    obj.foo()          '' Error!
    Dim base As Base = obj
    base.foo()         '' Okay
End Sub

请注意,这只是一个警告,不是错误。它只是预示了您将给客户机代码程序员带来的潜在痛苦。您可以很容易地隐藏警告,将Shadows关键字放在Load()方法前面。但是,当然要考虑避免客户端代码中的痛苦和痛苦,只需要选择另一个名称,这样就不会有歧义了。

您在第二个接口中重新定义了代码>加载< /代码>,如果您只在函数声明(或阴影)中使用重载就可以了。。为什么不将您的方法声明为
重载
,就像
重载函数加载(meetingType为布尔值)声明为列表(议程)
?编译器警告甚至暗示,我想使用所有三个加载函数。在C#中,此示例不会生成任何警告。这不是阴影,因为所有方法都有不同的特征。这是有效的。谢谢你,多米尼克