几乎是扩展属性
如何模拟扩展属性…
引言
扩展方法(Function
或 Sub
)是一种强大的工具,可以扩展原本密封的对象。它比创建 Class
扩展更容易,因为你不需要更新你的代码(可能已经部署),例如将 Dim nice As SomeClass
更改为 Dim nice As SomeClassExtendedAndNicer
。 显然,不同的情况需要不同的解决方案,你可能需要一个扩展的 Class
,但如果我可以使用扩展方法解决问题,我更喜欢使用扩展方法。扩展方法的一个巨大缺点是,你无法编写扩展属性!请参阅 MSDN 此处。
在本技巧中,我将展示如何(滥)用 Tag
属性作为扩展属性或 AlmostExtensionProperty
的代理。这个技巧的灵感来自于 StackOverflow 上的一个问答:VB extension property instead of extension method。
代码示例
首先,我们需要一个 Class
作为一些额外的扩展属性的容器。 你会为 ExtendedClass
或类似 AlmostExtensionProperty
编写这个 Class
Public Class ExtendedProps
Public StrA As String = "A"
Public DblB As Double = 2
Public BoolC As Boolean = True
'etc...
End Class
我将使用 Forms
Label
控件作为示例,使用 ExtendedClass
你可以编写如下代码
Public Class ExtendedLabel
Inherits Label
Public Sub New()
MyBase.New
_extProps = New ExtendedProps
End Sub
Private _extProps As ExtendedProps = Nothing
Public Property ExtraProperties() As ExtendedProps
Get
Return _extProps
End Get
Set
_extProps = value
End Set
End Property
End Class
到目前为止,没什么新鲜的。现在,创建一个 AlmostExtensionProperty
需要一个 Extension Module
并(滥)用 Label
控件的 Tag
对象,如下所示
Imports System.Runtime.CompilerServices
Public Module Extensions
<Extension()>
Public Function GetMoreProps(ByVal thisLabel As Label) As ExtendedProps
Try
Return CType(thisLabel.Tag,ExtendedProps)
Catch
Return Nothing
End Try
End Function
<Extension()>
Public Function SetMoreProps(ByVal thisLabel As Label, extraProps As ExtendedProps) As Boolean
Try
thisLabel.Tag = extraProps
Return True
Catch
Return False
End Try
End Function
End Module
两个扩展方法,通过 Label
控件的 Tag
对象暴露 ExtendedProps
类,这就是你所需要的。现在,如果你创建一个包含两个标签的窗体(一个常规 System.Windows.Forms.Label
和另一个特殊的 ExtendedLabel
),你可以测试 ExtendedProp
s
Public Class Main 'form
Public Sub New()
'Just a form with two Label controls:
'Dim labExtendedLabelClass As New ExtendedLabel()
'Dim labAlmostPropExt As New Label()
'Me.InitializeComponent()
labAlmostPropExt.SetMoreProps(New ExtendedProps)
Debug.Print("Property StrA from a Label with an AlmostPropertyExtension = " & _
labAlmostPropExt.GetMoreProps.StrA)
Debug.Print("Property StrA from a Label extended class = " & _
labExtendedLabelClass.ExtraProperties.StrA)
End Sub
End Class
运行此窗体将给出以下输出
Property StrA from a Label with an AlmostPropertyExtension = A
Property StrA from a Label extended class = A
不同的方法,相似的结果。
关注点
确实,这可能是 Tag
属性不太常用的用法。但是,对于所有不当编码的指责,我将回答:“谁告诉你编码世界是规范的……?”
历史
- 2016年3月25日:首次发布