Почему модуль Python Array обрабатывает строки и списки по-разному? - PullRequest
1 голос
/ 02 мая 2010

Мне трудно понять результат следующих утверждений:

>>> from array import array
>>> array('L',[0xff,0xff,0xff,0xff])
array('L', [255L, 255L, 255L, 255L])


>>> from array import array
>>> array('L','\xff\xff\xff\xff')
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ValueError: string length not a multiple of item size

Ответы [ 2 ]

3 голосов
/ 02 мая 2010

Это выполняется в 64-разрядной сборке Python, в которой array обрабатывает код типа 'L' как 64-разрядное целое число без знака.

>>> array('L','\xff\xff\xff\xff\xff\xff\xff\xff')
array('L', [18446744073709551615L])

Документация не очень понятна. Все это говорит о том, что 'L' это как минимум четыре байта.

1 голос
/ 02 мая 2010

В первом случае вы инициализируете массив из списка из 4 элементов. Это даст вам массив из 4 элементов: по одному для каждого значения в списке.

Во втором случае вы инициализируете массив из байтовой строки: байты в строке будут скопированы непосредственно в массив. Спецификатор 'L' создает массив длинных без знака, размер которых минимум 4 байта.

На моей машине (Windows 64 bit Python 2.6) инициализация из 4-байтовой строки работает нормально:

>>> a = array('L','\xff\xff\xff\xff')

>>> a.tostring()
'\xff\xff\xff\xff'

Я полагаю, какая версия Python, которую вы используете, имеет длину без знака, равную 8 байтам, а не 4. Попробуйте преобразовать созданный вами массив из списка обратно в строку и посмотрите, сколько байтов содержит:

>>> a = array('L',[0xff,0xff,0xff,0xff])
>>> a.tostring()
'\xff\x00\x00\x00\xff\x00\x00\x00\xff\x00\x00\x00\xff\x00\x00\x00'

P.S. Я предполагаю, что вы используете Python 2.x, в Python 3.x вместо этого вы бы получили TypeError.

...