在 VBA Excel 2007 中传递 Variant ByRef

Passing Variant ByRef in VBA Excel 2007

我在名为 MainForm

的用户窗体中声明了一个 public 变体变量
Public increaseArray As Variant
Public countryArray As Variant

然后在子按钮中单击主窗体:

Sub testButton_Click()

    Dim country As Variant

    Set countryArray = Module1.callSomeFunctionThatReturnsVariant(1)
    Set increaseArray = Module1.callSomeFunctionThatReturnsVariant(2)
    For Each country In countryArray
        Call Module1.createPage(country)
    Next country
End Sub

在模块 1 中我有:

Function callSomeFunctionThatReturnsVariant(ByVal testInt As Integer) As Variant
   .... do something when testInt = 1
   .... do something when testInt = 2
   callSomeFunctionThatReturnsVariant = someVariant
End Function

Public Sub createPage(ByVal country As String)

     Dim testInt As Integer

     ... do something
     testInt=insertSection(country, MainForm.increaseArray)
End Sub

Function insertSection(ByVal country As String, arr as Variant) As Integer
     Dim arrCountry As Variant

     For Each arrCountry In arr
         If country = "France" Then
             ...do something
             insertSection = 1
             Exit Function
         End If
     Next arrCountry

     insertSection = 2

End Function

MainForm.increaseArray 传递给 insertSection() 函数时出现 ByRef 参数类型不匹配错误。我试过使用 Function insertSection(ByVal country As String, ByVal arr as Variant) As Integer 但我得到了同样的错误。

如果我尝试在 createPage sub Dim testArray As Variant 中定义 Variant 变量并从其 getter 函数中获取 increaseArray Set testArray = MainForm.getterForIncreaseArray 我会收到类型不匹配错误... 如果我将 getter 函数直接传递给 insertSection 函数的调用者,我会得到 ByRef 参数类型不匹配...

请帮忙:)

根据 findwindow 的评论。您不能在表单内使用模块 1 中的内容,因为它超出了它的范围。相反,尝试将 module1 中的所有代码放入新的 class 模块中。从您的表单中实例化一个实例,它应该可以正常工作。

这个简单的代码工作正常。

不允许在用户窗体中声明 public 数组(因此使用变体作为伪装是个好主意)。

但是,函数不想接受将其作为参数作为合法数组传递,所以我使用了临时 'legit' 数组。

在用户窗体 1 上:

Option Explicit

Public a As Variant 'i would usually declare it like this : Public a() as variant, but public arrays not allowed in userforms (throws error)
'Private a() as variant ,  would not throw error (inside userform)

Private Sub UserForm_Initialize()
Dim i&
ReDim a(1 To 2) 'absolutely needed, it shows a is actually an array type
a(1) = 1
a(2) = 2
End Sub

Private Sub UserForm_Terminate()
Erase a
End Sub

在模块中: 选项显式

Sub test()
Load UserForm1
Dim b&
Call get_value(1, UserForm1.a, b)
Unload UserForm1
MsgBox b
End Sub

Sub get_value(ByVal i&, ByRef arr As Variant, ByRef answer As Long) ' function won't let it through, i used a sub with aditionnal variable as Byref.
answer = arr(i)
End Sub

通过调用 TEST 启动它。

注意:我没有成功地在函数中传递参数,因此在 SUB 中通过添加一个名为 Answer 的参数(即 Byref)来实现。

Note2 : 我回顾了我的旧代码,似乎你可以在函数中传递一个 byref 数组(伪装成变体),但可能是因为这个不是用 () 或其他什么声明的,它不想通过函数工作。

注意 3 : 在深入研究之后,我找到了一个使用函数的解决方案,正如我所想的那样,数组声明是麻烦制造者:

'in a module (use the same userform as before)
Sub test()
Load UserForm1
Dim b&
Dim i& 'counter
Dim Temp_Array() As Long 'as variant works too, but i filled it with numbers so as long is ok too
ReDim Temp_Array(LBound(UserForm1.a) To UBound(UserForm1.a))
'Temp_Array = UserForm1.a 'damn, i first thought this would work, in the same way you can fill a listbox in one simple line (wich would be a 3rd solution passing an array from the userform to a module)
For i = LBound(UserForm1.a) To UBound(UserForm1.a)
    Temp_Array(i) = UserForm1.a(i)
Next i
b = get_value(1, Temp_Array)
Erase Temp_Array
Unload UserForm1
MsgBox b
End Sub

Function get_value(ByVal i&, ByRef arr As Variant) As Long
get_value = arr(i)
End Function