同一属性的属性过程的定义是不一致的[使用数组]

时间:2016-02-12 23:46:13

标签: arrays vba excel-vba class excel

我遇到这个讨厌的错误消息(见标题) 我已经在这个网站和其他人的很多帖子上看到了它,这通常是一些愚蠢的错误,并尝试我可能无法看到我正在做的蠢事。

Public Property Get Contents() As Variant
    Contents() = pContents()
End Property

Public Property Let Contents(Values() As Variant)
    pContents = Values()
End Property

Public Property Get Content(Index As Integer) As String
    Content = pContents(Index)
End Property

Public Property Let Content(Index As Integer, Value As String)
...

目标是一对get,让两个允许整个数组被读/写,第二个允许通过索引读/写数组的各个元素。

根据这个:https://msdn.microsoft.com/en-us/library/office/gg251357.aspx

让属性声明的东西(是的,我对此相当新)对于类模块中的类必须满足某些要求(我很好奇为什么到底?)。据我所知,我的满足了这些要求:

My Let还有一个参数(2)而不是我的Get(1) - 我在这里假设" as string"括号的外部并不算作参数。 另外我在Let和Get中使用相同的类型(整数和字符串),我不需要Set,因此不应该成为问题。我也试过更改参数变量的名称无济于事。

所以请帮助我,出了什么问题,以后如何避免这个错误?

1 个答案:

答案 0 :(得分:1)

好吧,我似乎已经自己解决了这个问题,在这里发布答案以防万一! :)

将类属性设置为数组(并读取它们)时的注意事项

1)小心括号():不要在Let语句

中使用它们
Public Property Let ArrayProperty (newArray as variant)

而不是诱人的

Public Property Let ArrayProperty (newArray() as variant) 

同样,在使用此属性时请勿使用它们,例如:

Class1.ArrayProperty = myArray

myArray之后没有括号

2)检查属性中的数组不为空(myArray)让语句

将此处VBA: Don't go into loop when array is empty链接到帮助我完成此操作的答案,您似乎必须构建自己的函数或使用错误处理来执行此操作,

IsEmpty(myArray)

没有工作。

并且代码片段适合我的目的(归功于原始代码片段转到CreamyEgg):

Public Function IsEmptyArray(TestArray) As Boolean

Dim lngUboundTest As Long

lngUboundTest = -1
    On Error Resume Next
lngUboundTest = UBound(TestArray)
On Error GoTo 0

If lngUboundTest >= 0 Then    
IsEmptyArray = False
Else
IsEmptyArray = True
End If
End Function

3)记住你可能需要将你的属性数组重命名为Ubound(newArray),例如。

Public Property Let Contents (newArray as variant)
'redim pArray to size of proposed array
ReDim pArray(1 To UBound(newArray))
'above line will throw an exception if newArray is empty
    pArray = newArray   
end Property
4)故意使一个类属性成为一个空数组,我使用了一个临时数组变量,在标准模块的开头公开声明了一个sub

Public TempArray() As Variant
'outside of Sub ^^

Sub SetClass1ArrayToEmpty
    Erase TempArray
    class1.ArrayProperty = TempArray
End Sub

擦除方法将使数组为空,我使用它,因为我偶尔使用TempArray制作大小为1的数组,并希望确保它是空的

5)好消息,将范围设置为类属性似乎的工作方式与设置数组的范围相同,我使用了application.transpose(myRange)来避免一列的问题成为二维数组

class1.ArrayProperty = Application.Transpose(Range(myRange))

并且你有它,这里是工作的类(没有编译错误)

Public Property Get Contents() As Variant
    Contents() = pContents()
End Property

Public Property Let Contents(Values As Variant)
'checks for an empty array being passed to it first
If IsEmptyArray(Values) Then
    Erase pContents
Else
'redim pContents to size of proposed array
    ReDim pContents(1 To UBound(Values))
        pContents = Values
End If
End Property

Public Property Get Content(Index As Integer) As String
    Content = pContents(Index)
End Property

Public Property Let Content(Index As Integer, Value As String)

Select Case Index
    Case Is < 0
        'Error Handling
    Case Is > UBound(pContents) + 1
        'Error Handling
    Case Is = UBound(pContents) + 1  'append to end of array
        ReDim Preserve pContents(UBound(pContents) + 1)
        pContents(Index) = Value
    Case Else                        'replace some middle part of array
        pContents(Index) = Value
End Select

End Property

希望这有助于一些偷看!