Python - превратить содержимое файла в двоичный массив

Содержимое файла:

40 13 123
89 123 2223
4  12  0

Мне нужно сохранить весь файл .txt в виде двоичного массива, чтобы потом отправить его на серверную сторону, которая ожидает двоичный вход.


Я просмотрел документацию Python bytearray.  Я цитирую:

Возвращает новый массив байтов. Тип bytearray является изменяемой последовательностью целых чисел в диапазоне 0 <= x < 256. Он имеет большинство обычных методов изменчивых последовательностей, описанных в Mutable Sequence Types, а также большинство методов, которые имеют тип байтов, см. "Методы байтов и байтов".


Мои номера больше 256, мне нужна структура данных bytearray для чисел, которые больше 256.

Ответ 1

вы можете использовать подход array/memoryview

import array
a = array.array('h', [10, 20, 300]) #assume that the input are short signed integers
memv = memoryview(a)
m = memv.cast('b') #cast to bytes
m.tolist()

это тогда дает [10, 0, 20, 0, 44, 1]

В зависимости от использования, вы также можете:

L = array.array('h', [10, 20, 300]).tostring()
list(map(ord, list(L)))

это также дает [10, 0, 20, 0, 44, 1]

Ответ 2

Вы можете прочитать в текстовом файле и преобразовать каждое слово в int:

with open(the_file, 'r') as f:
    lines = f.read_lines()
    numbers = [int(w) for line in lines for w in line.split()]

Затем вам нужно упаковать numbers в двоичный массив с struct:

binary_representation = struct.pack("{}i".format(len(numbers)), *numbers)

Если вы хотите, чтобы эти данные записывались в двоичном формате, вы должны указать это при открытии целевого файла:

with open(target_file, 'wb') as f:
   f.write(binary_representation)

Ответ 3

Не bytearray

Из bytearray documentation, это всего лишь последовательность целых чисел в диапазоне 0 <= x < 256.

В качестве примера вы можете его инициализировать следующим образом:

bytearray([40,13,123,89,123,4,12,0])
# bytearray(b'(\r{Y{\x04\x0c\x00')

Так как целые числа уже хранятся в двоичном формате, вам не нужно ничего конвертировать.

Теперь ваша проблема: что вы хотите сделать с 2223?

>>> bytearray([2223])
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ValueError: byte must be in range(0, 256)

uint32 или массив int32?

Чтобы прочитать один файл, вы можете использовать:

import re
with open('test.txt') as f:
    numbers = [int(w) for line in f for w in re.split(' +', line)]
    print numbers
    #[40, 13, 123, 89, 123, 2223, 4, 12, 0]

После того, как у вас есть целочисленный список, вы можете выбрать соответствующий низкоуровневый структуру данных Numpy, возможно uint32 или int32.

Ответ 4

Мне это понадобилось для сервер-клиентский модуль, для которого одной из его функций требуется вход binary. Здесь можно найти различные типы сбережений здесь.

Client

myList = [5, 999, 430, 0]
binL = array.array('l', myList).tostring()
# call function with binL as parameter

В Сервер я восстановил список

k = list(array.array('l', binL))
print(k)
[5, 999, 430, 0]

Ответ 5

Попробуйте следующее:

input.txt:

40 13 123
89 123 2223
4  12  0

Код для синтаксического анализа ввода:

with open('input.txt', 'r') as _in:
    nums = map(bin, map(int, _in.read().split())) # read in the whole file, split it into a list of strings, then convert to integer, the convert to binary string

with open('output.txt', 'w') as out:
          out.writelines(map(lambda b: b + '\n', map(lambda n: n.replace('0b', ''), nums))) # remove the `0b` head from the binstrings, then append `\n` to every string in the list, then write to file

output.txt:

101000
1101
1111011
1011001
1111011
100010101111
100
1100
0

Надеюсь, что это поможет.