Reputation: 29
I saw quite a number of questions/answers along these lines, but after reading a bunch of them, I'm still confused. I'm sorry if this is the nᵗʰ time a variant of this has been asked.
I can't figure out why this code dies on line 5 with a "subscript out of range" error in VBA (Excel for Mac v16.38):
Public Function array_test()
Dim arr As Variant
Dim array_slice As Variant
arr = Range("TestData!B27:F32").Value2
array_slice = arr(2) 'dies here with error 9
array_test = array_slice
End Function
Looking at the values pane, arr is clearly a Variant/Variant(1 to 6, 1 to 5) with all the expected data. There is nothing special about the cells, just non-formula data.
Even if I change the declarations to arr() and array_slice() or remove ".Value2", I get the same results. Even trying Application.WorksheetFunction.Index(arr, 2) rather than arr(2) gets me nowhere.
What am I missing?
P.S. I'm a C/Python programmer normally, so I'm thinking of arrays in those terms.
Upvotes: 0
Views: 622
Reputation: 75840
Usually one would loop an 2D-array for it's elements, however, since you specifically mentioned you would like to slice it through VBA, you could use Application.Index
. For example try:
array_slice = Application.Index(arr, 2, 0) 'Slice 2nd row into 1D-array.
The idea here is to feed Application.Index
with a static '2' which represents the row of interest. In the same fashion you could slice a specific column of interest, though if you need this to be an 1D-array, you'd need to use Application.Transpose
, however there are limitations to this method:
With Application
array_slice = .Transpose(.Index(arr, 0, 2)) 'Slice 2nd column into 1D-array.
End With
Upvotes: 1
Reputation: 29171
When you copy data from a Range and the Range contains more than one cell, you get n 2-dimensional array in any case (even if you have only one row or one column).
To access a single value from that array, you have to provide both indices, like arr(2, 1)
. However, if you want to get a one-dimensional array, containing all values from a row (first index) or a column (second index), you need to create that array by your own - there is no slice
function in VBA. You can dimension an array at runtime using the ReDim
-command:
Dim array_slice(), i As Long
ReDim array_slice(LBound(arr, 1) To UBound(arr, 1))
For i = LBound(arr, 1) To UBound(arr, 1)
array_slice(i) = arr(i, 2)
Next i
To get the values of a column, use
Dim array_slice(), i As Long
ReDim array_slice(LBound(arr, 2) To UBound(arr, 2))
For i = LBound(arr, 2) To UBound(arr, 2)
array_slice(i) = arr(2, i)
Next i
Upvotes: 0