有没有办法在多个VBA脚本中使用相同的代码?

时间:2019-07-12 21:05:42

标签: excel vba

我有十二个宏,它们具有90%的相似代码,并且我试图找到一种方法,使每次需要对其进行普遍调整(例如更改密码)时都必须对其进行修改。

我确定了它们之间恒定的代码,并试图找到一种使最终代码采用以下格式的方法:

specific code
universal code A
specific code
universal code B

我首先尝试将通用代码另存为加载项,这将是理想选择,因为并非所有宏都位于同一文件中,并且我不想让用户(不是那么精通)多个文件。

当我以这种方式使用Application.Run进行操作时,我一直收到错误消息,说“该工作簿中的宏可能不可用,或者所有宏都可能被禁用了”。我所做的每一项检查都表明该加载项及其宏可用。

因此,我将通用代码移到了同一文件中并尝试了Call。并返回“运行时错误'-2147217908(80040e0c)”:未为命令对象设置命令文本。这与尝试在conn.State命令上执行有关。

我希望特定宏的结束代码看起来像这样:

Dim conn As New ADODB.Connection
Dim rs As New ADODB.Recordset

Sub getCreativeData()
    sheetName = "Retrieve Creative Data"

    Application.Run "uploader_portable.xlam!GetA"

    querystr = "select * from me_dev.upfront_dashboard_creative_data"

    Application.Run "uploader_portable.xlam!GetB"
End Sub

(很抱歉显示了这么多代码)

“ uploader_portable.xlam!GetA”现在看起来像这样:

Sub GetA()
    Application.EnableEvents = False
    Dim wb As Workbook
    Dim ws As Worksheet
    Set wb = ActiveWorkbook
    Set ws = ActiveSheet

    wb.Activate
    ws.Select

    ws.Range("A1:AF1000").ClearContents

    connString = "Driver={Amazon Redshift (x64)}; yadayadayada"

    'Connect to Database
    conn.Open connString
End Sub

“ uploader_portable.xlam!GetB”现在看起来像这样:

Sub GetB()
   ' Second set of code for the uploader retrieval add-in
    Set rs = conn.Execute(querystr, , adAsyncExecute)

    While conn.State = adStateExecuting + adStateOpen
        DoEvents
    Wend

    For x = 3 To rs.Fields.Count + 2
        ws.Cells(1, x) = rs.Fields(x - 3).Name
    Next

    If rs.RecordCount < Rows.Count Then
        ws.Range("C2").CopyFromRecordset rs
    End If    
End Sub

1 个答案:

答案 0 :(得分:0)

您沿正确的方向挖掘=必须重复使用代码! 从封装开始时,请拉出装饰器,层次结构,方法链,单元测试和测试驱动的开发。 也许您会编写这样的代码:

Sub GetA()
    conn.Open connString, _
            range_Strange_Clear( _
            App_Events(False))
End Sub

Function connString( _
        Optional s As String) _
        As String

    connString = "Driver={Amazon Redshift (x64)}; yadayadayada"

End Function

Function range_Strange_Clear( _
        Optional s As String) _
        As String

    Range("A1:AF1000").ClearContents

End Function

Function App_Events( _
        b As Boolean) _
        As String

    Application.EnableEvents = b

End Function