VB.Net中可覆盖属性的简写表示法不起作用

时间:2014-04-24 13:50:30

标签: vb.net class oop

在我的VB.Net代码中,我知道当我在类中声明一个属性时,我可以使用简写,例如,Public Property Prop1 As String和.Net自动创建一个私有变量{{1}我可以在课堂上引用。

我也知道我可以使用_Prop1_Prop1在我的代码中引用该变量。

既然我一直认为首选方法是使用私有变量,我总是试图在我的类中使用Prop1进行修改/编写代码。这就是我现在遇到的问题......

我有以下情况:

_Prop1

基本上,我在我的基类中将属性定义为可覆盖,现在当我到达Public Class MyClass_Base Public Overridable Property Prop1 As String = "val1" Public Sub Test() If _Prop1 = .... End Sub End Class Public Class MyClass Inherits MyClass_Base Public Overrides Property Prop1 As String = "val2" End Class 子例程时,Test()的值为_Prop1 。但是,Nothing的值为Prop1

在那里编程专家,处理这种情况的正确方法是什么? 我是否会忽略自动创建的prive变量val2并使用公共_Prop1,或者是否还有其他我应该添加/甚至不使用简写表示法来编写我自己的getter / setter逻辑确保事情按照我的意愿改变?

感谢!!!

2 个答案:

答案 0 :(得分:1)

我想你已回答了自己的问题。你绝对不应该依赖自己代码中隐藏的编译器机制。你引用了一个你没有声明的变量,并且框架中没有保证这个变量会存在(或者像你所发现的那样工作) - 这是一个使用它的黑客,所以不要吨。

除非你有充分的理由不这样做,否则类中的代码应该引用公共属性,就像使用类的代码一样。如果您正在使用自动属性,则执行此操作与使用私有变量之间没有区别。它还有一个好处,如果你以后再决定实现显式的getter和setter,你的代码不会破坏,并且你的新getter和setter会被调用。

在声明

时,探究获得意外结果的原因
  Public Overrides Property Prop1 As String = "val2"

您最终会得到两个不同的_Prop1变量 - MyClass_Base._Prop1MyClass._Prop1。然后当你调用Test()时,你正在调用基类方法,它将引用基类的_Prop1变量,该变量尚未设置为任何东西,因为你已经覆盖了隐式变量,getter和setter在子类中。

为了说明这一点,这类似于:

Public Class MyClass_Base
    Private _Prop1 As String = "val1"

    Public Sub Test()
        Console.WriteLine(_Prop1)
    End Sub
End Class

Public Class MySubClass
    Inherits MyClass_Base
    Private _Prop1 As String = "val2"
End Class

Sub Main()
    Dim class1 As New MyClass_Base
    Dim class2 As New MySubClass
    class1.Test()
    class2.Test()
End Sub

您的输出将是:

 val1
 val1

在上面的情况中,MyClass_Base._Prop1总是被初始化,但在你的情况下,它不是。在任何一种情况下,Test()方法都属于基类,所以它总是引用它自己的_Prop1而不是在子类中声明的同名变量。

如果你确实需要引用私人领域,无论出于何种原因,你必须非常小心你是如何做到的(以及后面的含义)。如果子类旨在以相同的方式使用它们自己的私有变量,那么执行此操作的任何方法本身都需要Overridable。不是建议你应该继续使用隐式变量,而是要证明:

Public Class MyClass_Base
    Public Overridable Property Prop1 As String = "val1"

    Public Overridable Sub Test()
        Console.WriteLine(_Prop1)
    End Sub
End Class

Public Class MySubClass
    Inherits MyClass_Base
    Public Overrides Property Prop1 As String = "val2"
    Public Overrides Sub Test()
        Console.WriteLine(_Prop1)
    End Sub
End Class

这里我们得到“预期”结果,因为MySubClass会覆盖test以引用自己的私有字段。最好只是坚持使用属性名称。

答案 1 :(得分:1)

来自documentation on Auto Implemented Properties

  

“为该属性指定的属性不适用于支持字段。”

这是需要对齐C#和VB.NET的领域之一。

C#(正确)不允许您访问自动实现的属性支持字段(没有一些复杂的工作)。老实说,我不知道你可以在VB中访问它。

所以这里的规则即使您可以访问自动实现的属性的支持字段,您也不应该直接修改它(也不需要)

如果您需要,那么您应该使用已定义的支持字段(带初始化)和明确的GetSet