Манипулирование двоичными данными в Python
Я открываю двоичный файл следующим образом:
file = open("test/test.x", 'rb')
и чтение строк в список. Каждая строка выглядит примерно так:
'\xbe\x00\xc8d\xf8d\x08\xe4.\x07~\x03\x9e\x07\xbe\x03\xde\x07\xfe\n'
Мне сложно манипулировать этими данными. Если я попытаюсь напечатать каждую строку, python замерзает и испускает звуковые сигналы (я думаю, там где-то есть двоичный звуковой код). Как я могу безопасно использовать эти данные? Как преобразовать каждый шестнадцатеричный номер в десятичный?
Ответы
Ответ 1
Чтобы распечатать его, вы можете сделать что-то вроде этого:
print repr(data)
В целом, как hex:
print data.encode('hex')
Для десятичного значения каждого байта:
print ' '.join([str(ord(a)) for a in data])
Чтобы распаковать двоичные целые числа и т.д. из данных, как если бы они были первоначально получены из структуры C-стиля, посмотрите struct.
Ответ 2
\xhh
- это символ с шестнадцатеричным значением hh. Другие символы, такие как .
и `~ ', являются нормальными символами.
Итерация по строке дает вам символы в ней по одному.
ord(c)
вернет целое число, представляющее символ. Например, ord('A') == 65
.
Это будет печатать десятичные числа для каждого символа:
s = '\xbe\x00\xc8d\xf8d\x08\xe4.\x07~\x03\x9e\x07\xbe\x03\xde\x07\xfe\n'
print ' '.join(str(ord(c)) for c in s)
Ответ 3
Как упомянутый выше анат, орд и гекс могут помочь вам.
Если вы хотите попытаться интерпретировать в файле какие-то структурированные двоичные данные, может оказаться полезным struct.
Ответ 4
Двоичные данные редко делятся на "строки", разделенные "\n" . Если это так, он будет иметь неявный или явный механизм эвакуации, чтобы различать "\n" как ограничитель строки и "\n" как часть данных. Чтение такого файла, как строки вслепую без знания механизма эвакуации, бессмысленно.
Чтобы ответить на ваши конкретные проблемы:
'\ x07' - это символ ASCII BEL, который изначально использовался для вызова колокола на телетайп-машине.
Вы можете получить целочисленное значение байта 'b', выполнив ord(b)
.
ОДНАКО, чтобы правильно обрабатывать двоичные данные, вам нужно знать, что такое макет. Вы можете иметь целые числа без знака (размер 1, 2, 4, 8 байт), числа с плавающей запятой, десятичные числа различной длины, строки фиксированной длины, строки с переменной длиной и т.д. И т.д. Добавлено осложнение происходит от того, записаны ли данные в бигэндианской моде или littleendian fashion. После того, как вы узнаете все вышеизложенное (или получите очень хорошие догадки), модуль структуры Python должен быть доступен для всех или большинства вашей обработки; может также быть полезен модуль ctypes.
Имеет ли формат данных имя? Если да, скажите нам; мы можем указать вам код или документы.
Вы спрашиваете: "Как мне безопасно использовать эти данные?" который задает вопрос: для чего вы хотите его использовать? Какие манипуляции вы хотите сделать?
Ответ 5
Вы пытаетесь распечатать данные, преобразованные в символы ASCII, которые не будут работать.
Вы можете безопасно использовать любой байт данных. Если вы хотите напечатать его как шестнадцатеричный, посмотрите на функции ord
и hex
/
Ответ 6
Используете ли вы read()
или readline()
? Вы должны использовать read(n)
для чтения n байтов; readline()
будет читать до тех пор, пока он не ударит по строке новой строки, которая может отсутствовать в двоичном файле.
В любом случае вам возвращают строку байтов, которые могут быть печатаемыми или непечатаемыми символами, и, вероятно, не очень полезны.
Вы хотите ord()
, который преобразует однобайтную строку в соответствующее целочисленное значение. read()
из файла по одному байту за раз и вызовите ord()
по результату или выполните итерацию по всей строке.