Почему функция VBA дает ошибку компиляции для коллекции, но не для строки - PullRequest
2 голосов
/ 08 июня 2019

Я пытаюсь передать коллекцию в функцию VBA, но получаю ошибку компиляции, которую я не могу исправить.

Это упрощенный пример, который дает ошибку.

Sub test()
    Dim fooString As String
    Dim fooCollection As collection
    Set fooCollection = New collection
    useString (fooString)
    useCollection (fooCollection)
End Sub

Public Function useString(foo As String)
    MsgBox ("here")
End Function

Public Function useCollection(foo As collection)
    MsgBox ("here")
End Function

Я не вижу, что я делаю иначе, чем показано в примерах, таких как показанный здесь: Как отсортировать коллекцию?

Это ошибка, которую я получаю (Ошибка компиляции: Аргумент не является обязательным):

enter image description here

Ответы [ 4 ]

5 голосов
/ 08 июня 2019

Вы получаете этот диалог из-за неявного «полезного» члена по умолчанию. В обозревателе объектов перейдите к Коллекции на панели классов, и в элементах вы увидите, что Элемент является элементом по умолчанию, обозначенным значком чирок.

Default member of Collection class

Вот еще один пример. Спросите себя, что он напечатает, и произнесите это вслух, прежде чем запускать код.

Public Sub DontWrapIt()
    Dim foo As Range
    Set foo = Sheet1.Range("A1")
    GiveMeARange foo
    GiveMeARange (foo)
End Sub

Private Sub GiveMeARange(ByVal param As Variant)
    Debug.Print TypeName(param)
End Sub

Обтекание объекта круглыми скобками приводит к его оценке, что вызывает неявный вызов «полезного» члена по умолчанию ... Для которого требуется параметр Index, который не указан - следовательно, «параметр не является обязательным».

1 голос
/ 08 июня 2019

Я не знаю, почему дается эта конкретная ошибка (в отличие от более информативной ошибки), но когда вы вызываете подпрограмму или функцию как подпрограмму (не используя возвращаемое значение), у вас не должно быть скобок вокруг аргументы. Следующие работы:

Sub test()
    Dim fooString As String
    Dim fooCollection As collection
    Set fooCollection = New collection
    useString fooString
    useCollection fooCollection
End Sub

Public Function useString(foo As String)
    MsgBox "here"
End Function

Public Function useCollection(foo As collection)
    MsgBox "here"
End Function

Но - если ваши функции действительно ничего не возвращают, возможно, вы могли бы просто определить их как подпрограммы для начала. В VBA на самом деле нет никакого смысла делать что-то, что на языке, подобном C, было бы пустой функцией.

0 голосов
/ 08 июня 2019

Это работает:

Sub test()
    Dim fooString As String
    Dim fooCollection As VBA.collection
    Set fooCollection = New VBA.collection
    fooCollection.Add "bar", "bar"
    useString (fooString)
    useCollection fooCollection
End Sub

Public Function useString(foo As String)
    MsgBox ("useString")
End Function

Public Function useCollection(ByRef foo As VBA.collection)
    MsgBox ("useCollection")
End Function
0 голосов
/ 08 июня 2019

Это просто вопрос вызова другого субэлемента ..

Если у него нет параметров, вы можете вызвать его только по имени:

useCollection или Call useCollection

Если у него есть параметры, то вы либо вызываете его без скобок, либо используете Call:

useCollection parameter или Call useCollection(parameter)

Sub test()
    Dim fooString As String
    Dim fooCollection As Collection
    Set fooCollection = New Collection
    useString (fooString)

    fooCollection.Add "test message", "test"
    useCollection fooCollection
    Call useCollection(fooCollection)
End Sub

Public Function useString(foo As String)
    MsgBox ("here")
End Function

Public Function useCollection(foo As Collection)
    MsgBox foo(1)
End Function

См.дополнительная информация об операторе Call :

При вызове процедуры не обязательно использовать ключевое слово Call .Однако если вы используете ключевое слово Call для вызова процедуры, требующей аргументов, argumentslist необходимо заключить в скобки.Если вы опустите ключевое слово Call , вы также должны опустить круглые скобки вокруг argumentslist .Если вы используете синтаксис Call для вызова любой встроенной или определяемой пользователем функции, возвращаемое значение функции отбрасывается

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...