python to - Преобразование hex в двоичный




9 Answers

Для решения левой задачи конечного нуля:

my_hexdata = "1a"

scale = 16 ## equals to hexadecimal

num_of_bits = 8

bin(int(my_hexdata, scale))[2:].zfill(num_of_bits)

Это даст 00011010 вместо обрезанной версии.

binary string

У меня есть ABC123EFFF.

Я хочу иметь 0010101011111000001001000111110111111111111 (т.е. двоичное представление с, скажем, 42 цифрами и ведущими нулями).

Как?




bin(int("abc123efff", 16))[2:]



Преобразование hex в двоичный

У меня есть ABC123EFFF.

Я хочу иметь 0010101011111000001001000111110111111111111 (т.е. двоичное представление с, скажем, 42 цифрами и ведущими нулями).

Короткий ответ:

Новые f-строки в Python 3.6 позволяют сделать это с использованием очень кратного синтаксиса:

>>> f'{0xABC123EFFF:0>42b}'
'001010101111000001001000111110111111111111'

или сломать это с помощью семантики:

>>> number, pad, rjust, size, kind = 0xABC123EFFF, '0', '>', 42, 'b'
>>> f'{number:{pad}{rjust}{size}{kind}}'
'001010101111000001001000111110111111111111'

Длительный ответ:

Фактически вы говорите, что у вас есть значение в шестнадцатеричном представлении, и вы хотите представить эквивалентное значение в двоичном формате.

Значение эквивалентности является целым числом. Но вы можете начать с строки, а для просмотра в двоичном формате вы должны заканчивать строку.

Преобразовать hex в двоичный, 42 цифры и ведущие нули?

У нас есть несколько прямых способов достижения этой цели, без хаков, использующих срезы.

Во-первых, прежде чем мы сможем сделать любую двоичную манипуляцию вообще, конвертируем в int (я предполагаю, что это в строковом формате, а не как литерал):

>>> integer = int('ABC123EFFF', 16)
>>> integer
737679765503

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

>>> integer = 0xABC123EFFF
>>> integer
737679765503

Теперь нам нужно выразить наше целое число в двоичном представлении.

Используйте встроенную функцию, format

Затем перейдите в format :

>>> format(integer, '0>42b')
'001010101111000001001000111110111111111111'

В нем используется mini-language спецификации форматирования.

Чтобы сломать это, вот его грамматическая форма:

[[fill]align][sign][#][0][width][,][.precision][type]

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

>>> spec = '{fill}{align}{width}{type}'.format(fill='0', align='>', width=42, type='b')
>>> spec
'0>42b'

и просто передайте это для форматирования

>>> bin_representation = format(integer, spec)
>>> bin_representation
'001010101111000001001000111110111111111111'
>>> print(bin_representation)
001010101111000001001000111110111111111111

Форматирование строк (Templating) с помощью str.format

Мы можем использовать это в строке с использованием метода str.format :

>>> 'here is the binary form: {0:{spec}}'.format(integer, spec=spec)
'here is the binary form: 001010101111000001001000111110111111111111'

Или просто поместите spec прямо в исходную строку:

>>> 'here is the binary form: {0:0>42b}'.format(integer)
'here is the binary form: 001010101111000001001000111110111111111111'

Строковое форматирование с новыми f-строками

Давайте продемонстрируем новые f-строки. Они используют одни и те же правила форматирования на мини-языке:

>>> integer = 0xABC123EFFF
>>> length = 42
>>> f'{integer:0>{length}b}'
'001010101111000001001000111110111111111111'

Теперь давайте включим эту функциональность в функцию, чтобы поощрять повторное использование:

def bin_format(integer, length):
    return f'{integer:0>{length}b}'

И сейчас:

>>> bin_format(0xABC123EFFF, 42)
'001010101111000001001000111110111111111111'    

В стороне

Если вы просто хотели кодировать данные как строку байтов в памяти или на диске, вы можете использовать метод int.to_bytes , который доступен только в Python 3:

>>> help(int.to_bytes)
to_bytes(...)
    int.to_bytes(length, byteorder, *, signed=False) -> bytes
...

А так как 42 бита, деленные на 8 бит на байт, равны 6 байтам:

>>> integer.to_bytes(6, 'big')
b'\x00\xab\xc1#\xef\xff'



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

Ключевой бит для понимания:

(n & (1 << i)) and 1

Который будет генерировать либо 0, либо 1, если установлен i-й бит n.


import binascii

def byte_to_binary(n):
    return ''.join(str((n & (1 << i)) and 1) for i in reversed(range(8)))

def hex_to_binary(h):
    return ''.join(byte_to_binary(ord(b)) for b in binascii.unhexlify(h))

print hex_to_binary('abc123efff')

>>> 1010101111000001001000111110111111111111

Изменить: используя «новый» тернарный оператор:

(n & (1 << i)) and 1

Станет:

1 if n & (1 << i) or 0

(Какой TBH я не уверен, насколько это читаемо)




bin(int("abc123efff", 16))[2:]

'1010101111000001001000111110111111111111'
`bin(int("abc123efff", 16))[2:].zfill(50)`

'00000000001010101111000001001000111110111111111111'

(Число 50 сообщит zfill что вы хотите завершить строку нулями до тех пор, пока длина строки не будет равна 50 ).




Замените каждую шестую цифру соответствующими 4 двоичными цифрами:

1 - 0001
2 - 0010
...
a - 1010
b - 1011
...
f - 1111



Я добавил расчет количества бит для заполнения в решении Onedinkenedi. Вот результирующая функция:

def hextobin(h):
  return bin(int(h, 16))[2:].zfill(len(h) * 4)

Где 16 - база, из которой вы конвертируете (шестнадцатеричный), а 4 - количество бит, которое вам нужно представлять каждую цифру, или базу данных 2 шкалы.




У меня есть короткая надежда, которая помогает :-)

input = 'ABC123EFFF'
for index, value in enumerate(input):
    print(value)
    print(bin(int(value,16)+16)[3:])

string = ''.join([bin(int(x,16)+16)[3:] for y,x in enumerate(input)])
print(string)

сначала я использую ваш вход и перечисляю его, чтобы получить каждый символ. то я преобразовываю его в двоичный и обрезаю с 3-й позиции до конца. Трюк для получения 0 заключается в том, чтобы добавить максимальное значение ввода -> в этом случае всегда 16 :-)

краткая форма метода соединения. Наслаждаться.




import binascii
hexa_input = input('Enter hex String to convert to Binary: ')
pad_bits=len(hexa_input)*4
Integer_output=int(hexa_input,16)
Binary_output= bin(Integer_output)[2:]. zfill(pad_bits)
print(Binary_output)
"""zfill(x) i.e. x no of 0 s to be padded left - Integers will overwrite 0 s
starting from right side but remaining 0 s will display till quantity x
[y:] where y is no of output chars which need to destroy starting from left"""



Related