Может ли массив иметь значения другого типа данных
В общем случае массивы не будут иметь значений другого типа данных, но когда используется метод Items для извлечения данных из объекта словаря. Это делает данные другого типа данных.
Может ли кто-нибудь уточнить меня по этому поводу, возможно ли для массивов иметь значения другого типа данных?
Option Explicit
Dim D, i, Arr
Set D = CreateObject("Scripting.Dictionary")
D.CompareMode = VbTextCompare
D.Add "1", 56
D.Add "2", 78
D.Add "3", "John"
D.Add "4", 100
Arr = D.Items
For i=0 to ubound(Arr) Step+1
Msgbox Arr(i)
Next
1 ответ
VBScript очень слабо типизирован. Все переменные являются вариантами (разных подтипов: целые числа, строки, объекты, ...). Коллекции могут содержать предметы всех подтипов; предметы могут быть даже разных подтипов.
Даже ключи словаря не обязательно должны быть строками; они также могут быть объектами. В связи с этим вопросом, касающимся словарей и массивов, я должен добавить: массивы могут быть элементами, но не ключами словаря:
>> Set d = CreateObject("Scripting.Dictionary")
>> d.Add "Company", Array("microsoft", "apple")
>> WScript.Echo Join(d("Company"))
>> a = d("Company") <== array assignment in VBScript COPIES!
>> a(1) = "samsung"
>> WScript.Echo Join(a)
>> WScript.Echo Join(d("Company"))
>>
microsoft apple
microsoft samsung
microsoft apple
>> d.Add a, "won't work"
>>
Error Number: 5
Error Description: Invalid procedure call or argument
Подтип, с которым следует быть осторожным, это Fixed Array (определяется с помощью Dim a(ConstNumber)
). Элементы довольно неограничены, но я был бы удивлен, если бы вы могли поместить Fixed Array в коллекцию.
Обновление (без фиксированных массивов):
Фиксированный массив и его элементы хранятся особым образом для повышения производительности. Я ничего не знаю о деталях, но это особый тип массива (который не может расти).
Поместить что-либо в коллекцию означает: поместить в нее копию чего-либо (type + value(s)). Если что-то является простой переменной или массивом, вы теряете связь с оригиналом (снова подумав, чтобы указать на это, @Ansgar). Если что-то является объектом, копия ссылки (объекта) по-прежнему дает вам доступ к данным оригинала.
Копия Fixed Array, которая попадает в коллекцию (хорошо, тест использует только словарь) теряет специальный тип:
Option Explicit
Dim Af(0) : Af(0) = "fixed"
ReDim Ad(0) : Ad(0) = "dyn"
WScript.Echo 0, Af(0), Ad(0)
Dim dicX : Set dicX = CreateObject("Scripting.Dictionary")
dicX(0) = Af
dicX(1) = Ad
WScript.Echo 1, dicX(0)(0), dicX(1)(0)
Af(0) = UCase(Af(0))
Ad(0) = UCase(Ad(0))
WScript.Echo 2, Af(0), Ad(0)
WScript.Echo 3, dicX(0)(0), dicX(1)(0)
grow dicX(0)
grow dicX(1)
WScript.Echo 4, Join(dicX(0)), Join(dicX(1))
grow Ad
WScript.Echo 5, Join(Ad)
grow Af
Sub grow(a)
ReDim Preserve a(Ubound(a) + 1)
a(1) = "array"
WScript.Echo "**", Join(a)
End Sub
выход:
cscript doa.vbs
0 fixed dyn
1 fixed dyn
2 FIXED DYN
3 fixed dyn
** fixed array
** dyn array
4 fixed dyn
** DYN array
5 DYN array
E:\trials\SoTrials\answers\15008949\vbs\doa.vbs(23, 3) Microsoft VBScript runtime error: This array is fixed or temporarily locked
** fixed array
строка доказывает, что массив передан grow
больше не фиксируется; это не того же типа, что и Af
это не может расти.