当使用VBA中的一类?(When to use a Class in VBA?)

2019-06-17 16:59发布

什么时候适合使用在Visual Basic中的一类应用程序(VBA)?

我假设的加速发展和减少引入错误的是支持OOP大多数语言的共同利益。 但随着VBA,有没有一个具体的标准?

Answer 1:

这取决于谁去开发和维护的代码。 典型的“超级用户”黑客小特设宏的应用程序可能会作家以及通过使用类混淆。 但对于严重的事态发展,原因使用类是相同的其他语言。 你有相同的限制VB6 - 没有继承 - 但你可以用接口具有多态性。

良好的使用类别为代表的实体,和实体的集合。 例如,常常看到VBA代码副本的Excel范围成二维阵列,然后操纵与像代码的二维阵列:

Total = 0
For i = 0 To NumRows-1
    Total = Total + (OrderArray(i,1) * OrderArray(i,3))
Next i

这是更具可读性的范围内复制与适当命名的属性,类似对象的集合:

Total = 0
For Each objOrder in colOrders
    Total = Total + objOrder.Quantity * objOrder.Price
Next i

另一个例子是使用类来实现的RAII设计图案(谷歌它)。 例如,有一件事我可能需要做的是取消保护工作表,做一些操作,然后再保护它。 使用类确保工作表总是会被再次即使在你的代码中出现错误的保护:

--- WorksheetProtector class module ---

Private m_objWorksheet As Worksheet
Private m_sPassword As String

Public Sub Unprotect(Worksheet As Worksheet, Password As String)
    ' Nothing to do if we didn't define a password for the worksheet
    If Len(Password) = 0 Then Exit Sub

    ' If the worksheet is already unprotected, nothing to do
    If Not Worksheet.ProtectContents Then Exit Sub

    ' Unprotect the worksheet
    Worksheet.Unprotect Password

    ' Remember the worksheet and password so we can protect again
    Set m_objWorksheet = Worksheet
    m_sPassword = Password
End Sub

Public Sub Protect()
    ' Protects the worksheet with the same password used to unprotect it
    If m_objWorksheet Is Nothing Then Exit Sub
    If Len(m_sPassword) = 0 Then Exit Sub

    ' If the worksheet is already protected, nothing to do
    If m_objWorksheet.ProtectContents Then Exit Sub

    m_objWorksheet.Protect m_sPassword
    Set m_objWorksheet = Nothing
    m_sPassword = ""
End Sub

Private Sub Class_Terminate()
    ' Reprotect the worksheet when this object goes out of scope
    On Error Resume Next
    Protect
End Sub

然后,您可以用它来简化你的代码:

Public Sub DoSomething()
   Dim objWorksheetProtector as WorksheetProtector
   Set objWorksheetProtector = New WorksheetProtector
   objWorksheetProtector.Unprotect myWorksheet, myPassword

   ... manipulate myWorksheet - may raise an error

End Sub 

当此子退出,objWorksheetProtector超出范围,和工作表再次被保护。



Answer 2:

我认为标准是一样的其他语言

如果你需要绑在一起的几个数据块和一些方法,并专门处理在创建对象时/终止,类是理想会发生什么

说,如果你有,当你打开一个表格,其中一人花费很长的时间,这火的几个程序,你可能决定要每个时间阶段......

你可以创建一个具备明显的函数的方法来启动和停止,那么你可以添加一个函数来检索的时间,到目前为止并在一个文本文件,用巧夺天工的工艺是定时的名称的参数举报秒表类。 你可以写逻辑只记录最慢的表现进行调查。

然后,您可以添加一个进度条的对象与方法来打开和关闭,并显示当前操作的名称,在MS和可能的时间沿着时间根据以前存储的报告等其余

另一个例子是,如果你不喜欢访问的用户群的垃圾,你可以创建在登录电子方式进出和功能组级的用户访问控制/审计/记录的某些动作/跟踪误差等自己的用户类

当然,你可以做到这一点使用一组不相关的方法和大量的变量传递的,但拥有这一切封装在一个类似乎只是更好的给我。

你迟早亲近VBA的限制,但其相当强大的语言,如果你的公司将您与它其实你可以得到一些很好的,复杂的解决方案出来。



Answer 3:

与更复杂的API函数打交道时类是非常有用的,特别是当他们需要的数据结构。

例如,GetOpenFileName()和则GetSaveFileName()函数采取与许多成员的OPENFILENAME结构同步。 你可能不需要采取一切他们的优势,但它们的存在和应该初始化。

我喜欢的结构(UDT)和API函数声明包装成一个CFileDialog类。 在Class_Initialize事件设置结构成员的默认值,这样,当我使用这个类,我只需要设置我想改变(通过房产手续)的成员。 标志常量被实现为一个枚举。 因此,举例来说,选择一个电子表格,打开,我的代码可能是这样的:

Dim strFileName As String
Dim dlgXLS As New CFileDialog

With dlgXLS
  .Title = "Choose a Spreadsheet"
  .Filter = "Excel (*.xls)|*.xls|All Files (*.*)|*.*"
  .Flags = ofnFileMustExist OR ofnExplorer

  If OpenFileDialog() Then
    strFileName = .FileName
  End If
End With
Set dlgXLS = Nothing

类设置默认目录到我的文档,但如果我想我可以与InitDir属性更改它。

这是一类可以如何在一个VBA应用带来许多有益的只是一个例子。



Answer 4:

我不会说有一个具体的标准,但我从来没有真正找到了VBA代码使用类有用的地方。 在我的脑海里它是如此依赖于现有的模型周围的Office应用程序,添加额外的抽象对象模型的外面只会带来混乱。

这并不是说一个无法找到一个有用的地方在VBA类,或使用类做的非常有用的东西,只是我从来没有发现他们在这种环境中非常有用。



Answer 5:

您也可以重复使用VBA代码,而无需使用实际的类。 举例来说,如果你有一个叫做,VBACode。 您可以访问任何功能或子与下面的语法中的任何模块:

VBCode.mysub(param1, param2)

如果创建模板/文件的引用(如你将一个dll),您可以从其他项目以同样的方式引用代码。



Answer 6:

开发软件,甚至与Microsoft Access,使用面向对象的编程通常是一个很好的做法。 这将允许物体被松耦合,具有许多优点以及允许在未来的可扩展性。 这基本上意味着,在你的系统中的对象将更少地依赖于对方,所以重构变得轻松了许多。 你可以做到这一点是使用类模块的访问。 缺点是,你不能在VBA执行类的继承和多态。 最后,还有用类,只是最佳实践没有硬性的规定。 但请记住,当你的应用程序的增长,越容易使用类维护。



Answer 7:

对于数据递归(又名BOM处理),自定义类是极为有益的,我觉得有时候是必不可少的。 你可以做一个递归函数没有类模块,但是很多数据问题不能得到有效解决。

(我不知道为什么人们不出来兜售BOM库集VBA。也许XML工具已产生了效果。)

多形式的情况下,是一类常见的应用程序(很多自动化问题是无法解决的,否则),我认为问题是关于自定义类。



Answer 8:

我使用类,当我需要做一些事情,一类会做到最好:)例如,如果你需要(或拦截)事件做出响应,那么你需要的类。 有些人讨厌UDT(用户定义类型),但我喜欢他们,所以我用他们,如果我想简单的英语自我记录代码。 Pharmacy.NCPDP是一个更容易阅读,然后strPhrmNum :)但UDT是有限的,所以说我希望能够设置Pharmacy.NCPDP,拥有所有其他属性填充。 我也想使它所以你不能意外地改变数据。 然后,我需要一个类,因为你没有在UDT等具有只读属性

另一个需要考虑的仅仅是简单的可读性。 如果你正在做复杂的数据结构,它往往是有益知道你只需要调用Company.Owner.Phone.AreaCode然后试图跟踪的一切是结构化的。 特别是对于谁必须维护代码库你离开2年后的人:)

我自己的两分钱是“码对于目的”。 不要使用类没有理由。 但是,如果你有充分的理由再去做:)



Answer 9:

我用类,如果我想创建的代码的自密封封装,我将跨越是遇到为不同客户很多VBA项目中使用。



Answer 10:

您可以定义访问SQL包装类,比记录集和querydefs更方便。 例如,如果要更新基于一个标准,另一个相关的表的表,你不能使用连接。 你可以建立一个VBA recorset和的QueryDef要做到这一点,但是我觉得它更容易使用的类。 此外,您的应用程序可以有一些概念需要超过2个表,这可能是更好的伊莫使用类为。 例如,你的应用程序跟踪事件。 回复...}。 为了跟踪所有的查询和参与的关系,OOP可以是有益的。 这是一种解脱,能够做到Incident.Update(XXX),而不是所有的编码...



Answer 11:

我不明白为什么,VBA的标准将是另一种语言有什么不同,特别是如果你指的是VB.NET。



文章来源: When to use a Class in VBA?
标签: oop vba class