Как правило, при передаче массива что-то подпрограмме в VBA самое простое решение - объявить параметр как Variant
.
Объявление параметра как массива означает, чтовызывающая подпрограмма должна передавать именно этот тип массива.Если подпрограмма объявлена для получения массива Long
, вы должны передать массив Long
.Не Integer
, не Variant
.То же самое верно, если подпрограмма объявлена для получения массива Variant
- вы должны передать массив Variant
.
Теперь Variant
- это своего рода магический тип данных.Вариант может быть что угодно - даже массив.Когда вы объявляете параметр как Variant
и передаете Long
(или String
, или ...), VBA Runtime Engine позаботится о том, чтобы был создан Variant
, сохранил содержимое Long
(или String
или ...) и отслеживает, что он в данный момент хранит.
Если вы передадите массив этому варианту, VBA сохранит этот массив в Variant
(возможно, только для справки)и отслеживает не только тот факт, что он содержит массив, но также и тип массива.
Однако, если вы объявите параметр как массив Variant
, среда выполнения не сможет выполнить свою магию.Вы говорите Runtime, что получите кучу Variants
, но затем вы передаете кучу Integer
.Среда выполнения должна будет преобразовывать каждый элемент массива из Integer
в Variant
- и это просто не делает этого.Вместо этого компилятор VBA жалуется или, при вызове через Application.Run
, выдает «Несоответствие типов» ошибка времени выполнения.
Существуют некоторые функции, которые могут помочь вам получить информацию о том, что (в настоящее время) хранится в варианте: IsArray
сообщает вам, если Variant
содержит ошибку, а VarType
даст вам информацию о типе (дополнительную информацию о VarType
см. https://docs.microsoft.com/en-us/office/vba/language/reference/user-interface-help/vartype-function). LBound
и Ubound
предоставят вам размер массива. Единственное, что вы не можете получить, - это информацию о размерах массива. В редком случае вы не знаете о количестве измерений, https://stackoverflow.com/a/6902088/7599798 может дать вам решение.