I’m presently populating my array Securities with the following code:
Option Base 1
Securities = Array(Worksheets(3).Range("A8:A" & SymbolCount).Value)
This produces a 2-dimensional array where every address is (1…1,1…N). I want a 1-dimensional array (1…N).
How can I either (a) populate Securities as a 1-dimensional array, or, (b) efficiently strip Securities to a 1-dimensional array (I’m stuck at a with each loop).
asked Oct 4, 2011 at 13:57
I know you already accepted an answer but here is simpler code for you:
If you are grabbing a singe row (with multiple columns) then use:
Securities = application.transpose(application.transpose _
(Worksheets(3).Range("A8:A" & SymbolCount).Value))
If you are grabbing a single column (with multiple rows) then use:
Securities = application.transpose(Worksheets(3).Range("A8:A" & SymbolCount).Value)
So, basically you just transpose twice for rows and once for columns.
Update:
Large tables might not work for this solution (as noted in the comment below):
I used this solution in a large table, and I found that there is a limitation to this trick:
Application.Transpose(Range("D6:D65541").Value)
‘runs without error, butApplication.Transpose(Range("D6:D65542").Value)
‘run-time error 13 Type mismatch
Update 2:
Another problem you might have as mentioned in the comments:
If one exceeds 255 characters, the function fails.
It has been a long time since I worked with Excel VBA but this might be a general limitation of accessing the data this way?
answered Oct 4, 2011 at 17:00
Jon49Jon49
4,3844 gold badges36 silver badges73 bronze badges
9
Sub test2()
Dim arTmp
Dim securities()
Dim counter As Long, i As Long
arTmp = Range("a1").CurrentRegion
counter = UBound(arTmp, 1)
ReDim securities(1 To counter)
For i = 1 To counter
securities(i) = arTmp(i, 1)
Next i
MsgBox "done"
End Sub
answered Oct 4, 2011 at 14:16
iDevlopiDevlop
24.6k11 gold badges89 silver badges147 bronze badges
6
This will reflect the answer iDevlop gave, but I wanted to give you some additional information on what it does.
Dim tmpArray As Variant
Dim Securities As Variant
'Dump the range into a 2D array
tmpArray = Sheets(3).Range("A8:A" & symbolcount).Value
'Resize the 1D array
ReDim Securities(1 To UBound(tmpArray, 1))
'Convert 2D to 1D
For i = 1 To UBound(Securities, 1)
Securities(i) = tmpArray(i, 1)
Next
Probably the fastest way to get a 1D array from a range is to dump the range into a 2D array and convert it to a 1D array. This is done by declaring a second variant and using ReDim
to re-size it to the appropriate size once you dump the range into the first variant (note you don’t need to use Array(), you can do it as I have above, which is more clear).
The you just loop through the 2D array placing each element in the 1D array.
I hope this helps.
answered Oct 6, 2011 at 4:46
GaijinhunterGaijinhunter
14.5k4 gold badges50 silver badges57 bronze badges
2
If you read values from a single column into an array as you have it then I do think you will end up with an array that needs to be accessed using array(1, n)
syntax.
Alternatively, you can loop through all cells in your data and add them into an array:
Sub ReadIntoArray()
Dim myArray(), myData As Range, cl As Range, cnt As Integer, i As Integer
Set myData = Worksheets(3).Range("A8:A" & SymbolCount) //Not sure how you get SymbolCount
ReDim myArray(myData.Count)
cnt = 0
For Each cl In myData
myArray(cnt) = cl
cnt = cnt + 1
Next cl
For i = 0 To UBound(myArray) //Print out the values in the array as check...
Debug.Print myArray(i)
Next i
End Sub
answered Oct 4, 2011 at 14:33
Alex PAlex P
12.2k5 gold badges51 silver badges69 bronze badges
6
Копирование значений из диапазона ячеек в массив и обратно с помощью VBA Excel. Простейшие примеры обмена значениями между диапазоном и массивом.
Как известно, VBA обрабатывает информацию в массивах значительно быстрее, чем в ячейках рабочего листа Excel. Поэтому, при работе с большими объемами данных, удобнее использовать массивы, чем наблюдать во время выполнения кода за мерцанием изображения на экране или просто смотреть в неизменную картинку, если обновление экрана отключено (Application.ScreenUpdating = False). Здесь обмен значениями между массивом и диапазоном ячеек будет вполне уместен.
Копирование значений из диапазона ячеек в массив
Чтобы скопировать значения из диапазона ячеек в массив, необходимо объявить переменную универсального типа (As Variant) и присвоить ей значения диапазона ячеек с помощью оператора присваивания (=):
Dim a As Variant a = Range(«A1:C3») |
VBA Excel автоматически преобразует объявленную переменную в двумерный массив, соответствующий размерности диапазона ячеек, в нашем случае в массив — a(1 To 3, 1 To 3), и заполняет его значениями. Нумерация измерений массивов, созданных таким образом, начинается с единицы (1).
Можно, в этом случае, объявить сразу динамический массив, чтобы изначально указать, что эта переменная будет массивом. Так как свойством диапазона ячеек по умолчанию в VBA Excel является значение (Value), его можно в коде явно не указывать, но, при желании, можно и указать. Получится такая конструкция, аналогичная первой:
Dim a() As Variant a = Range(«A1:C3»).Value |
Стоит отметить, что для копирования значений из диапазона ячеек в массив можно использовать только обычную переменную или динамический массив универсального типа (Variant). VBA Excel автоматически преобразовывает их в двумерный массив. Если объявить двумерный массив с указанной заранее размерностью, использовать его не получится, будет сгенерирована ошибка с сообщением: Can’t assign to array (Нельзя назначать массив).
Копирование значений из массива в диапазон ячеек
Значения в диапазон ячеек добавляются из массива с помощью оператора присваивания (=):
Range(«A6:F15») = a ‘или Range(«A6:F15»).Value = a ‘где a — переменная двумерного массива |
Обратите внимание, что вставить значения в диапазон ячеек можно только из двумерного массива. Размерность такого массива может начинаться с нуля (0). Количество элементов в измерениях массива должно совпадать с количеством строк и столбцов в диапазоне ячеек. Если вам нужно вставить значения в одну строку или в один столбец, укажите размерность единственной строки или единственного столбца как (0) или (1 To 1), если вы хотите использовать нумерацию измерений своего массива с единицы. Например, для записи десяти значений из массива в одну строку можно объявить такой массив — massiv(9, 0), или в один столбец — massiv(0, 9).
Для вставки значений в диапазон ячеек из массива идеально подойдет массив, созданный для копирования в него значений из диапазона. В этом случае, данные с рабочего листа Excel переносятся в массив, обрабатываются и, после обработки, вставляются обратно в ту же или другую таблицу на том же или другом рабочем листе.
Обмен значениями между двумя диапазонами
Обмен значениями можно осуществить в VBA Excel не только между массивом и диапазоном, но и между двумя диапазонами одинаковой размерности:
Range(«B2:D6») = Range(«G7:I11»).Value |
У диапазона, являющегося источником значений, обязательно должно быть указано свойство Value
.
Если диапазон ячеек, принимающий значения, по размеру меньше диапазона-источника, то он будет заполнен полностью:
Range(«B2:D6») = Range(«G5:L13»).Value |
Если принимающий диапазон ячеек по размеру больше передающего, то часть его будет заполнена значениями диапазона-источника, а остальные ячейки — значениями #Н/Д
:
Range(«B2:D6») = Range(«G7:H9»).Value |
Простейшие примеры обмена значениями
Эти примеры составлены так, чтобы вам не пришлось совершать лишних действий, просто скопируйте их в свой модуль любой книги Excel с поддержкой макросов и запустите по очереди на выполнение.
Пример 1
Заполнение двумерного массива значениями и и их присвоение диапазону ячеек на рабочем листе Excel:
Sub Test1() Dim a(2, 2) As Variant a(0, 0) = «телепузик» a(0, 1) = «журналист» a(0, 2) = «ящерица» a(1, 0) = «короед» a(1, 1) = «утенок» a(1, 2) = «шмель» a(2, 0) = 200 a(2, 1) = 300 a(2, 2) = 400 Range(«A1:C3»).Value = a End Sub |
В данном случае переменная массива не обязательно должна быть универсального типа (As Variant), например, если бы в нее записывались только текстовые данные, ее можно было бы объявить как строковую (As String), и все бы работало.
Пример 2
Объявление обычной переменной универсального типа, присвоение ей значений из диапазона ячеек «A1:C3», записанных кодом первого примера, и вставка этих значений из полученного двумерного массива в диапазон «D10:F12»:
Sub Test2() Dim a As Variant a = Range(«A1:C3») Range(«D10:F12») = a End Sub |
Естественно, указанные диапазоны ячеек расположены на активном листе.
Пример 3
Допустим, на рабочем листе «Лист1» в ячейках «A1:A5» записано количество какого-то товара, а в ячейках «B1:B5» — его цена. Необходимо к этой информации добавить сумму каждого товара, умножив количество на цену, и перенести данные на «Лист2».
Sub Test3() Dim a As Variant, i As Long a = Лист1.Range(«A1:C5») For i = 1 To 5 a(i, 3) = a(i, 1) _ * a(i, 2) Next Лист2.Range(«A1:C5») = a End Sub |
Массив создан сразу с размерностью 5×3 с элементами под суммы. Даже если на первом листе в ячейках «C1:C5» есть какие-то значения, в массиве они будут перезаписаны результатами вычислений.
Копирование значений из массива в массив
Этот пример показывает, как в VBA Excel можно скопировать значения из одного массива в другой:
Sub Test4() Dim arr1, arr2 arr1 = Range(«G7:I11») arr2 = arr1 Range(«B2:D6») = arr2 End Sub |
Sub example_1() 'двумерные массивы (на выбор) Dim x x = Range("A1", Cells(Rows.Count, 1).End(xlUp)).Value x = Range("A1", Cells(5, Columns.Count).End(xlToLeft)).Value x = Range("A1").CurrentRegion.Value With Sheets("Sheet1") x = .Range("A1:D" & .Cells(Rows.Count, 1).End(xlUp).Row).Value x = .UsedRange.Value End With End Sub
Sub example_2() 'одномерный массив (на выбор), индексация всегда с 1 Dim x With Range("A1", Cells(Rows.Count, 1).End(xlUp)) 'из столбца x = WorksheetFunction.Transpose(.Value) End With With WorksheetFunction 'из строки x = .Transpose(.Transpose(Range("A1", Cells(1, Columns.Count).End(xlToLeft)).Value)) End With x = Application.Index(Range("A1", Cells(1, Columns.Count).End(xlToLeft)).Value, 1, 0) End Sub
Sub example_3() 'одномерный массив без дубликатов из столбца с заголовком Dim x, i& i = ActiveSheet.UsedRange.Columns(1).Rows.Count x = Filter(Evaluate("TRANSPOSE(IF(COUNTIF(OFFSET(a2:a" & i & ",0,0,ROW(1:" & i - 1 & _ ")),a2:a" & i & ")=1,a2:a" & i & ",CHAR(126)))"), "~", 0) Range("B1").Resize(UBound(x) + 1).Value = WorksheetFunction.Transpose(x) End Sub
Sub example_4() 'одномерный массив без дубликатов из столбца без заголовка Dim x With ActiveSheet.Cells(1).CurrentRegion.Columns(1) x = Filter(.Parent.Evaluate("TRANSPOSE(IF(COUNTIF(OFFSET(" & .Address & ",0,0,ROW(1:" & .Rows.Count & _ "))," & .Address & ")=1," & .Address & ",CHAR(126)))"), "~", 0) End With Range("B1").Resize(UBound(x) + 1).Value = WorksheetFunction.Transpose(x) End Sub
Sub example_5() 'одномерный массив без пустых значений из столбца Dim x With Range("A1", Cells(Rows.Count, 1).End(xlUp)) x = Split(Replace(Join(Filter(Split("~" & Join(Application.Transpose(.Value), "~|~") & "~", "|"), _ "~~", False), "|"), "~", ""), "|") End With Range("B1").Resize(UBound(x) + 1).Value = WorksheetFunction.Transpose(x) End Sub
Sub example_6() 'массив из строки (только для англ. алфавита!) Dim myStr As String, x: myStr = "AsDfghErt" x = Split(StrConv(myStr, 64), Chr(0)) Range("B1").Resize(UBound(x)).Value = WorksheetFunction.Transpose(x) End Sub
eagl69 Пользователь Сообщений: 114 |
#1 09.11.2020 11:35:29 Добрый день! Подскажите как сохранить в массив данные из выделенного диапазона ячеек?
|
||
Mershik Пользователь Сообщений: 8277 |
#2 09.11.2020 11:38:00 eagl69,
точнее
Изменено: Mershik — 09.11.2020 11:44:50 Не бойтесь совершенства. Вам его не достичь. |
||||
Jack Famous Пользователь Сообщений: 10848 OS: Win 8.1 Корп. x64 | Excel 2016 x64: | Browser: Chrome |
#3 09.11.2020 11:54:44
здравствуйте отсюда Изменено: Jack Famous — 09.11.2020 11:56:04 Во всех делах очень полезно периодически ставить знак вопроса к тому, что вы с давних пор считали не требующим доказательств (Бертран Рассел) ►Благодарности сюда◄ |
||
vikttur Пользователь Сообщений: 47199 |
#4 09.11.2020 15:58:37
Новый оператор, который выводит в одно Immediate весь масив?
|
||||
Jack Famous Пользователь Сообщений: 10848 OS: Win 8.1 Корп. x64 | Excel 2016 x64: | Browser: Chrome |
#5 09.11.2020 17:06:21
приветствую Изменено: Jack Famous — 09.11.2020 17:06:36 Во всех делах очень полезно периодически ставить знак вопроса к тому, что вы с давних пор считали не требующим доказательств (Бертран Рассел) ►Благодарности сюда◄ |
||
vikttur Пользователь Сообщений: 47199 |
Jack, упор был сделан не на вывод массива, а на новый оператор ) |
Ігор Гончаренко Пользователь Сообщений: 13746 |
#7 09.11.2020 21:53:18
все. выделенный диапазон в массиве а Изменено: Ігор Гончаренко — 09.11.2020 21:56:48 Программисты — это люди, решающие проблемы, о существовании которых Вы не подозревали, методами, которых Вы не понимаете! |
||||
Jack Famous Пользователь Сообщений: 10848 OS: Win 8.1 Корп. x64 | Excel 2016 x64: | Browser: Chrome |
Ігор Гончаренко, это Mershik ещё в #2 показал — какой смысл дублировать?… Во всех делах очень полезно периодически ставить знак вопроса к тому, что вы с давних пор считали не требующим доказательств (Бертран Рассел) ►Благодарности сюда◄ |
eagl69 Пользователь Сообщений: 114 |
#9 10.11.2020 09:44:51 Друзья, спасибо за ответы! Еще дополнения, допустим у нас 100 строк, я выделил в столбце А ячейки с 20 по 30 получил массив:
далее мне нужен такой же массив но с колонки С, как его создать если у нас выделен диапазон в столбце А? В итоге у меня должно быть 2 массива с данными из одинаковых строк.
Изменено: eagl69 — 10.11.2020 09:45:41 |
||||
Ігор Гончаренко Пользователь Сообщений: 13746 |
#10 10.11.2020 10:00:10
валите в эту тему все вопросы, что накопились у вас по Excel Программисты — это люди, решающие проблемы, о существовании которых Вы не подозревали, методами, которых Вы не понимаете! |
||
eagl69 Пользователь Сообщений: 114 |
#11 10.11.2020 10:25:47 Большое спасибо за помощь! |
0 / 0 / 0
Регистрация: 15.05.2014
Сообщений: 11
1
В одномерный массив записать данные из диапазона ячеек
15.05.2014, 20:16. Показов 4322. Ответов 2
В одномерный массив записать данные из диапазона ячеек, заключенных между двумя числами, целая часть которых начинается цифрой 1, а заканчивается цифрой 9 (если второго числа нет, то выбрать все ячейки до конца столбца). Полученный массив записать во второй столбец. Найти минимальное значение положительных элементов массива и записать его в ячейку С1.
Visual Basic | ||
|
0