VBA最佳实践:使用小型子函数和函数,在例程之间传递值

问题描述 投票:0回答:3

我从互联网上了解到,我们的vba宏(子和函数)应该或多或少与屏幕大小相同。

但是我的所有代码完全相反:a有一个调用函数和小子函数的huuuge主子函数。

我的问题是:如果我决定将我的主要巨型子转换为小型子(sub1,sub2,sub3等),那么保留在sub1中分配的变量的值并在sub2中使用它的最佳方法应该是什么,在sub2中分配并在sub3中使用它,依此类推?如果我对这个问题没有答案,我会将这些值保存在表格中,但也许这样会给我带来麻烦,我现在看不到。谢谢你的帮助。

vba
3个回答
1
投票

以下两种方法都可行。在我个人看来,方法1使代码更简单(您可以避免将大量参数传递给每个宏),但根据您的需要,您可以选择其中一个。

全局变量

您的代码看起来像这样:

'Global variables declaration
Dim a As Integer
Dim b As Integer
'
Public Sub mainRoutine()
    setA '<-- call first macro
    setB '<-- call second macro
    MsgBox a + b '<-- show A + B (2 + 3 = 5) 
End Sub
'code of sub-routines
Private Sub setA()
    a = 2 '<-- since a is global, it will keep the value
End Sub
Private Sub setB()
    b = 3 '<-- since b is global, it will keep the value
End Sub

请注意:global表示此变量的值将适用于程序的所有执行。程序结束后将释放内存。

将变量作为ByRef参数传递

Public Sub mainRoutine()
    Dim a As Integer '<-- a is local
    a = 2 '<-- setting a to 2
    setA a '<-- passing a as ByRef parameter 
    MsgBox a '<-- a is now 3
End Sub
Private Sub setA(ByRef a As Integer)
    a = 3 '<-- setting a as 3. 
End Sub

当然,上述方法只允许在执行a = 2/3期间保留mainRoutine。但是,如果在某些时候您执行另一个堆栈调用的另一个宏(例如电子表格中的另一个按钮),您将无法像在方法1中那样访问a的值。

重要提示:不,电子表格中的变量不是一个好主意,除非您在关闭并重新打开电子表格后不需要保留该值(在这种情况下,您将使用电子表格作为一种数据库)。


3
投票

Sub或Function应具有单一且明确的目的,由其名称来表示。如果您在这些块中分解代码,您将知道这些方法需要和提供的信息。与此同时,它们将变得更小。如果您必须在尺寸和清晰度之间进行选择,请注意清晰度。 不要将您的值放在工作表中。这只是一种使用全局变量的不同且效率较低的方法,这是你应该避免的(不是不惜一切代价,而是差不多)。


1
投票

VBA可以被认为是面向对象的编程语言(OOP)。它有OOP的4个支柱中的3个:

  • 抽象化
  • 封装
  • 多态性

这在Is VBA an OOP language, and does it support polymorphism?中讨论过

OOP意味着理解SOLID原则。

  • 单一责任原则
  • 开放封闭原则
  • 子替换
  • 接口隔离原理
  • 依赖倒置原则

最佳做法是遵守这些原则,首先是单一责任原则。

这表明你的函数/ subs应该有一个责任,并专注于做一件事。

优点(除其他外):

代码复杂性和依赖性降低意味着:

1)更容易调试,因为您的跟踪功能会引发错误的子/功能

2)可以更容易地围绕基于单一责任的代码构建单元测试。

3)可以更容易地插入更广泛的代码库

要在子/函数之间使用变量,请考虑:

1)公共变量和/或

2)将变量作为参数传递

其他信息:

OOP VBA pt.1: Debunking Stuff

© www.soinside.com 2019 - 2024. All rights reserved.