【问题标题】:Can you inherit a sub new (Constructor) with parameters in VB?你可以在VB中继承一个带有参数的子新(构造函数)吗?
【发布时间】:2009-04-25 22:11:06
【问题描述】:

在下面的代码中我收到编译错误

Error Too many arguments to 'Public Sub New()'

Dim TestChild As ChildClass = New ChildClass("c") 上。我没有在TestChild.Method1() 上收到它,即使它们都在我继承的基类上。

Public Class BaseClass
    Public ReadOnly Text As String
    Public Sub New(ByVal SetText As String)
        Text = SetText
    End Sub
    Public Sub New()
        Text = ""
    End Sub
End Class

Public Class ChildClass
    Inherits BaseClass
End Class

Public Class TestClass
    Sub Test()
        Dim TestChild As ChildClass = New ChildClass("c")
        TestChild.Method1()
    End Sub
End Class

我可以将子类更改为:

Public Class ChildClass
    Inherits BaseClass
      Public Sub New (ByVal SetText As String)
      MyBase.New(SetText)
    End Class
End Class

如下所示,但我不必为方法 1 或其他继承的方法这样做,我正在寻找尽可能干净的代码。这可能是系统中继承参数化 New 语句的限制,但我无法在任何地方找到它的文档。如果需要,那么我想查看文档。

【问题讨论】:

    标签: vb.net inheritance constructor new-operator


    【解决方案1】:

    您看到的行为是“设计使然”。子类不会从其基类型继承构造函数。子类负责定义它自己的构造函数。此外,它必须确保它定义的每个构造函数都隐式或显式调用基类构造函数或链接到同一类型的另一个构造函数。

    您需要在所有子类上定义相同的构造函数,并通过 MyBase.New 显式链接回基本构造函数。示例

    Class ChildClass
      Inherits BaseClass
      Public Sub New(text As String)
        MyBase.New(text)
      End Sub
    End Class
    

    您要查找的文档是 VB 语言规范的第 9.3.1 节。

    我认为最相关的部分是以下(大致从第二页开始)

    如果类型不包含实例构造函数声明,则会自动提供默认构造函数。默认构造函数只是调用直接基类型的无参数构造函数。

    这并没有明确声明子类不会继承构造函数,但这是该声明的副作用。

    【讨论】:

    • JaredPar,感谢您提供明确的答案并指向文档。我喜欢有来源,这样我就可以尽可能深入了解细节。
    • 很好的解释,但我想知道为什么不能这样做。允许它很简单。
    • 现在单击文档链接会生成一个页面,其中包含“Visual Studio 2003 Retired Technical documentation”文本。
    • docs.microsoft.com/en-us/dotnet/visual-basic/reference/… 页面上关于构造函数的部分有一段话:“构造函数是允许控制初始化的特殊方法。它们在程序开始后或创建类型的实例时运行。与其他成员不同,构造函数不是继承的,也不会将名称引入类型的声明空间。构造函数只能由对象创建表达式或 .NET Framework 调用;它们永远不会被直接调用。"
    【解决方案2】:

    参数化构造函数不能像实例方法一样被继承。您需要在子类中实现构造函数,然后使用 MyBase 调用父类的构造函数。

    Public Class ChildClass
        Inherits BaseClass
    
        Public Sub New (ByVal SetText As String)
          MyBase.New(SetText)
        End Class
    End Class
    
    Public Class TestClass
      Public TestChild AS New ChildClass("c")
    End Class
    

    此限制不是 VB 特有的。据我所知,这在 C#、Java 或 C++ 中肯定是不可能的。

    这是一篇与 C++ 相同问题的相关帖子:
    c-superclass-constructor-calling-rules

    【讨论】:

    • 感谢您的建议。我按照您在 Visual Studio 中的建议更新了代码,但仍然收到相同的编译错误。我还更新了帖子,以便其他人看到您的建议被纳入。还有其他想法吗?
    • 对不起,我看错了你的帖子。目标是继承新方法,因此我不必在所有子类中重复代码。如何在不按照您的建议在子类中编码的情况下访问基类中的新方法。
    • 何塞,为了清楚起见,我进行了编辑。我不需要在子类中实现方法1。是否需要在子类中实现构造函数。不能直接继承?
    • 何塞,感谢您帮助我澄清我的问题。感谢您对其他 OO 语言的引用。它有助于理解这个概念。
    • 我还没有 15 个代表。当我达到那个目标时,我会停止回购。
    猜你喜欢
    • 1970-01-01
    • 2021-10-13
    • 2011-04-21
    • 1970-01-01
    • 2018-03-31
    • 2014-02-03
    • 2020-01-09
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多