当前位置:  开发笔记 > 编程语言 > 正文

VBA的隐藏功能

如何解决《VBA的隐藏功能》经验,为你挑选了9个好方法。

VBA语言的哪些功能要么记录不清,要么根本不经常使用?



1> Oorang..:

此技巧仅适用于Access VBA,Excel和其他人不允许这样做.但是,您可以通过在模块名称前加下划线来使对象浏览器隐藏标准模块.只有在您更改对象浏览器以显示隐藏对象时,才会显示该模块.

这个技巧适用于所有基于vb6的VBA版本中的Enums.您可以通过在括号中包含它的名称来创建Enum的隐藏成员,然后在其前面添加下划线.例:

Public Enum MyEnum
    meDefault = 0
    meThing1 = 1
    meThing2 = 2
    meThing3 = 3
    [_Min] = meDefault 
    [_Max] = meThing3 
End Enum

Public Function IsValidOption(ByVal myOption As MyEnum) As Boolean
    If myOption >= MyEnum.[_Min] Then IsValidOption myOption <= MyEnum.[_Max]
End Function

在Excel-VBA中,您可以通过将单元格括在括号中来引用单元格,括号也可以用作评估命令,允许您评估公式语法:

Public Sub Example()
    [A1] = "Foo"
    MsgBox [VLOOKUP(A1,A1,1,0)]
End Sub

通过将LSet与相同大小的用户定义类型组合,您可以在不使用MemCopy(RtlMoveMemory)的情况下传递原始数据:

Public Sub Example()
    Dim b() As Byte
    b = LongToByteArray(8675309)
    MsgBox b(1)
End Sub

Private Function LongToByteArray(ByVal value As Long) As Byte()
    Dim tl As TypedLong
    Dim bl As ByteLong
    tl.value = value
    LSet bl = tl
    LongToByteArray = bl.value
End Function

Octal和Hex Literals实际上是无符号类型,它们都输出-32768:

Public Sub Example()
    Debug.Print &H8000
    Debug.Print &O100000
End Sub

如上所述,在括号内传递变量会导致它传递ByVal:

Sub PredictTheOutput()
    Dim i&, j&, k&
    i = 10: j = i: k = i
    MySub (i)
    MySub j
    MySub k + 20
    MsgBox Join(Array(i, j, k), vbNewLine), vbQuestion, "Did You Get It Right?"
End Sub

Public Sub MySub(ByRef foo As Long)
    foo = 5
End Sub

您可以将字符串直接分配给字节数组,反之亦然:

Public Sub Example()
    Dim myString As String
    Dim myBytArr() As Byte
    myBytArr = "I am a string."
    myString = myBytArr
    MsgBox myString
End Sub

"Mid"也是一名运营商.使用它可以覆盖字符串的特定部分而无需VBA众所周知的慢字符串连接:

Public Sub Example1()
    ''// This takes about 47% of time Example2 does:
    Dim myString As String
    myString = "I liek pie."
    Mid(myString, 5, 2) = "ke"
    Mid(myString, 11, 1) = "!"
    MsgBox myString
End Sub

Public Sub Example2()
    Dim myString As String
    myString = "I liek pie."
    myString = "I li" & "ke" & " pie" & "!"
    MsgBox myString
End Sub



2> Swanny..:

Mid()语句有一个重要但几乎总是错过的功能.这就是Mid()出现在赋值的左侧而不是出现在右侧或表达式中的Mid()函数的位置.

规则是如果目标字符串不是字符串文字,并且这是对目标字符串的唯一引用,并且插入的段的长度与要替换的段的长度匹配,则该字符串将被视为操作可变.

那是什么意思?这意味着如果您将一个大型报表或一个庞大的字符串列表构建到单个字符串值中,那么利用它将使您的字符串处理更快.

这是一个受益于此的简单类.它为您的VBA提供了与.Net相同的StringBuilder功能.

' Class: StringBuilder

Option Explicit

Private Const initialLength As Long = 32

Private totalLength As Long  ' Length of the buffer
Private curLength As Long    ' Length of the string value within the buffer
Private buffer As String     ' The buffer

Private Sub Class_Initialize()
  ' We set the buffer up to it's initial size and the string value ""
  totalLength = initialLength
  buffer = Space(totalLength)
  curLength = 0
End Sub

Public Sub Append(Text As String)

  Dim incLen As Long ' The length that the value will be increased by
  Dim newLen As Long ' The length of the value after being appended
  incLen = Len(Text)
  newLen = curLength + incLen

  ' Will the new value fit in the remaining free space within the current buffer
  If newLen <= totalLength Then
    ' Buffer has room so just insert the new value
    Mid(buffer, curLength + 1, incLen) = Text
  Else
    ' Buffer does not have enough room so
    ' first calculate the new buffer size by doubling until its big enough
    ' then build the new buffer
    While totalLength < newLen
      totalLength = totalLength + totalLength
    Wend
    buffer = Left(buffer, curLength) & Text & Space(totalLength - newLen)
  End If
  curLength = newLen
End Sub

Public Property Get Length() As Integer
  Length = curLength
End Property

Public Property Get Text() As String
  Text = Left(buffer, curLength)
End Property

Public Sub Clear()
  totalLength = initialLength
  buffer = Space(totalLength)
  curLength = 0
End Sub

以下是如何使用它的示例:

  Dim i As Long
  Dim sb As StringBuilder
  Dim result As String
  Set sb = New StringBuilder
  For i = 1 to 100000
    sb.Append CStr( i)
  Next i
  result = sb.Text



3> mandroid..:

VBA本身似乎是一个隐藏的功能.我知道多年来一直使用Office产品的人不知道它甚至是套件的一部分.

我在这里发布了多个问题,但对象浏览器是我的秘密武器.如果我需要忍者快速编写代码,但我不熟悉dll,对象浏览器可以挽救我的生命.它使得学习类结构比MSDN更容易.

Locals Window也非常适合调试.在代码中暂停,它将显示当前命名空间中的所有变量,名称以及它们的当前值和类型.

谁能忘记我们的好朋友立即窗口?它不仅适用于Debug.Print标准输出,而且您也可以输入命令.需要知道VariableX是什么?

?VariableX

需要知道那个细胞是什么颜色的?

?Application.ActiveCell.Interior.Color

事实上,所有这些窗口都是使用VBA提高工作效率的绝佳工具.



4> Dirk Vollmar..:

这不是一个功能,但是我在VBA(和VB6)中已经多次看到错误:在方法调用中添加了括号,它将改变语义:

Sub Foo()

    Dim str As String

    str = "Hello"

    Bar (str)
    Debug.Print str 'prints "Hello" because str is evaluated and a copy is passed

    Bar str 'or Call Bar(str)
    Debug.Print str 'prints "Hello World"

End Sub

Sub Bar(ByRef param As String)

    param = param + " World"

End Sub


这是语言的一个特点.添加括号允许您传递参数ByVal而不是ByRef.有关详细信息,请参阅http://msdn.microsoft.com/en-us/library/chy4288y.aspx上的"如何:强制参数传递值".
+1我还没有找到一个实际需要Call关键字的例子.`call foo(bar)`总是可以用`foo bar`代替,所以Call似乎是多余的.根据VBA关于SO的问题,许多人似乎都没有意识到括号不需要调用Sub,所以我们可以称之为一个知之甚少的功能

5> Raj More..:

隐藏的功能

    虽然它是"Basic",但您可以使用OOP - 类和对象

    您可以进行API调用


对于那些说VBA中的OO不是OO的人来说,克服它.接口继承也是继承 - 它只是一种不同的类型.

6> DaveParillo..:

可能在VBA中记录最少的功能是您只能通过在VBA对象浏览器上选择"显示隐藏的成员"来公开的功能.隐藏成员是VBA中的那些功能,但不受支持.您可以使用它们,但Microsoft可能会随时消除它们.他们都没有提供任何文件,但你可以在网上找到一些.可能最受关注的这些隐藏功能可以访问VBA中的指针.对于体面的写作,请查看; 不那么轻量级 - Shlwapi.dll

记录,但可能更加模糊(无论如何都是excel)使用ExecuteExcel4Macro来访问属于整个Excel应用程序实例而不是特定工作簿的隐藏全局命名空间.



7> guillermooo..:

您可以使用Implements关键字实现接口.



8> eksortso..:

字典.没有它们,VBA几乎毫无价值!

参考Microsoft Scripting Runtime,Scripting.Dictionary用于任何足够复杂的任务,并且从此过上幸福的生活.

Scripting Runtime还为您提供了FileSystemObject,强烈建议使用它.

从这里开始,然后挖掘一下......

http://msdn.microsoft.com/en-us/library/aa164509%28office.10%29.aspx



9> CtrlDot..:

键入VBA.将显示所有内置函数和常量的intellisense列表.

推荐阅读
农大军乐团_697
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有