VBA早期与晚期绑定 - 现实生活中的表现差异

时间:2018-04-12 06:37:34

标签: vba performance binding ms-word


我正在编写一个强大的Word宏,它将用于几台不同机器上的各种单词。
我在许多专家VBA论坛上都很红,早期绑定总是优于后期绑定,因为它在性能方面要优越得多等
根据我的逻辑,它感觉如此 - 然而令人信服地证明了无益的好处 - 在可用性方面恰恰相反,因为我不想要确保在可能运行的所有机器上打勾的那些lib-references的痛苦。

我已经尝试过ThisWorkbook.VBProject.References.AddFromGUID "{420B2830-E718-11CF-893D-00A0C9054228}", 1, 0。它会以编程方式添加引用,但是它需要在机器上启用安全信任以进行代码操作。
那么我已经设置了一个测试来比较1000次早期和晚期的绑定字典操作。我也玩过其他测试设置,如ScreenUpdating,DoEvents,Debug.Print,以查看每个测试设置的性能影响。
到目前为止,我看到的是,早期与晚期绑定本身在任何设置中都没有可测量的性能差异(除了任何运行之间的10%随机波动)。 VBA Guru-s我对你对这个故事的关注感兴趣,为什么我应该使用Early binding,或者它真的是真正的生活使用方式的优势。

我的TestCode是这样的:

Sub HeadingDefinitionWords_test()
    Application.ScreenUpdating = False
    Dim tm As Long
    tm = timeGetTime
    Dim DefinitionRangeBackup As Range, DefinitionRange As Range
    Dim kEy As Variant, i As Long, k As Integer
    Dim TempList As Object: Set TempList = CreateObject("Scripting.Dictionary")
    'Dim TempList As Scripting.Dictionary: Set TempList = New Scripting.Dictionary
    For i = 1 To 1000
    'Call HeadingDefinitionWords(Selection.Range.Duplicate, TempList)
    '''
         Set DefinitionRange = Selection.Range.Duplicate
         Set DefinitionRangeBackup = DefinitionRange.Duplicate
         '-
            With DefinitionRange.Find: .ClearFormatting: .Text = "([a-z])([A-Z])"
                .Forward = True: .Wrap = wdFindStop: .Format = False: .MatchCase = False: .MatchWholeWord = False: .MatchAllWordForms = False
                .MatchSoundsLike = False: .MatchWildcards = True
            End With
        '-
            With DefinitionRange: While .Find.Execute And .InRange(DefinitionRangeBackup)
            '-
                .Expand Unit:=wdWord
            '-
                If Not TempList.Exists(Trim(DefinitionRange.Text)) Then TempList.Add Trim(DefinitionRange.Text), Trim(DefinitionRange.Text)
            '-
                DefinitionRange.Collapse wdCollapseEnd
            Wend: End With

        '''
        For Each kEy In TempList
            'Debug.Print kEy
            If k = 50 Then
                'Debug.Print k
                k = 1
            Else
                k = k + 1
            End If
            'DoEvents
        Next

    Next

    Dim tma As Long
    tma = timeGetTime
    Debug.Print tma - tm

    Application.ScreenUpdating = True
End Sub

1 个答案:

答案 0 :(得分:3)

不确定这应该作为答案,但是,嘿,

早期结合对于开发工作(速度和智能感知)是优选的。由于您提到的原因,后期绑定经常用于分发。除非您绝对100%确定您的用户设置,否则在生产中使用延迟绑定会更安全。

引用Word MVP website

早期绑定的优点

您的代码运行速度要快得多,因为它们都可以预先编译。使用后期绑定,与您声明为对象的应用程序相关的代码实际上必须在运行时进行编译。

因为您的代码都可以预先编译,所以调试要容易得多 - 选择Debug + Compile,编译器将能够发现在您使用后期绑定时可能会遗漏的语法错误。

您在项目中拥有对智能感知的完全访问权限(键入关键字和点以获取该关键字支持的属性和方法的弹出列表,选择一个以插入它;键入关键字并按F1启动帮助主题关于那个关键词)。

您可以通过对象浏览器和VBA帮助完全访问应用程序的对象模型。

您可以访问应用程序的内置常量。例如,如果要从Excel自动化Word,则可以使用:

Dim objWord As Word.Application 
Set objWord = New Word.Application 

With objWord 
    .Visible = True 
    .Activate 
    .WindowState = wdWindowStateMaximize 
    .Documents.Open ("c:\temp\temp.doc") 
End With 

此外,当您键入

.WindowState =

您将获得支持的常量的弹出式列表,只需从列表中选择wdWindowStateMaximize

如果您使用后期绑定,则需要使用:

.WindowState = 1

..你需要知道(通过在Word的对象浏览器中查找)常量"wdWindowStateMaximize"的值恰好为1。

所有这些使得使用早期绑定进行编程比使用后期绑定更容易。

后期绑定的优点

主要优点是使用后期绑定的代码更确定是与版本无关的

如果将Word 97项目中的引用设置为“Microsoft Excel 8.0对象库”,则项目将在安装了Office 2000的计算机上运行正常。 Word 2000动态更改引用到“Microsoft Excel 9.0对象库”。

但正如他们着名的说,YMMV。在某些情况下发现了问题。例如,如果在安装了Office 2000的计算机上运行包含对Excel 8.0对象库的引用的Word 97项目,它将运行正常,但除非您保存项目,否则可能会偶尔出现“无法打开宏存储”错误在Word 2000中。如果您将其保存在Word 2000中,引用将更改为Excel 9.0对象库。

因此,如果您使用早期绑定并支持混合环境,尽管存在维护开销,最安全的方法是创建单独的Word 97和Word 2000版本的插件。

项目包含的引用越多,文件大小越大,编译时间越长。

某些编程环境不允许您创建对其他应用程序的引用。

如果你真的想开始深入研究COM对象,那么v-tables等可能从以下参考开始:

参考文献:

  1. Microsoft Blurb:Using early binding and late binding in Automation