2008-10-14 17 views
6

Uso de la función PHP pack(), He convertido una cadena en una representación hexadecimal binario:¿Cómo puedo descomprimir datos formateados hexadecimales binarios en Python?

$string = md5(time); // 32 character length 
$packed = pack('H*', $string); 

El H * formato significa "cadena Hex, nibble alto primero".

Para descomprimir esto en PHP, simplemente usaría la función unpack() con el indicador de formato H *.

¿Cómo desempacaré esta información en Python?

+0

tiene su terminología horriblemente confundida. – hop

+0

@hop: Aparte de "hex binario", todo está bien. Hay una pequeña diferencia en el vocabulario entre idiomas. Me confundió al principio hasta que leí la definición del paquete de PHP(), pero es solo una cuestión de utilizar diferentes términos. – Brian

Respuesta

12

Hay una manera fácil de hacer esto con el módulo binascii:

>>> import binascii 
>>> print binascii.hexlify("ABCZ") 
'4142435a' 

A menos que esté malinterpretando algo sobre el orden de los nibbles (primero el mordisco alto es el predeterminado), ¡eso debería ser perfectamente suficiente!

Además, los objetos hashlib.md5 de Python tienen un método hexdigest() para convertir automáticamente el resumen MD5 a una cadena hexadecimal ASCII, por lo que este método ni siquiera es necesario para los resúmenes MD5. Espero que ayude.

8

En Python utiliza el módulo struct para esto.

>>> from struct import * 
>>> pack('hhl', 1, 2, 3) 
'\x00\x01\x00\x02\x00\x00\x00\x03' 
>>> unpack('hhl', '\x00\x01\x00\x02\x00\x00\x00\x03') 
(1, 2, 3) 
>>> calcsize('hhl') 
8 

HTH

+3

Nota: "h" significa algo diferente en struct que "nibble codificado como hex" - se refiere a un entero de 16 bits. – Brian

+0

Como en sHort int. – XTL

11

No hay código correspondiente "hexagonal mordisco" para struct.pack, por lo que se tendrá que empacar manualmente en bytes principio, como:

hex_string = 'abcdef12' 

hexdigits = [int(x, 16) for x in hex_string] 
data = ''.join(struct.pack('B', (high <<4) + low) 
       for high, low in zip(hexdigits[::2], hexdigits[1::2])) 

O mejor, solo puedes usar el códec hexadecimal. es decir.

>>> data = hex_string.decode('hex') 
>>> data 
'\xab\xcd\xef\x12' 

para desempaquetar, se puede codificar el resultado de nuevo a hexadecimal de manera similar

>>> data.encode('hex') 
'abcdef12' 

Sin embargo, cabe destacar que por su ejemplo, probablemente no hay necesidad de tomar el de ida y vuelta a través de una representación hexadecimal en absoluto cuando codifica Solo usa el resumen binario md5 directamente. es decir.

>>> x = md5.md5('some string') 
>>> x.digest() 
'Z\xc7I\xfb\xee\xc96\x07\xfc(\xd6f\xbe\x85\xe7:' 

Esto es equivalente a la representación de su paquete() ed. Para obtener la representación hexadecimal, utilice el mismo método de desempaquetado arriba:

>>> x.digest().decode('hex') 
'acbd18db4cc2f85cedef654fccc4a4d8' 
>>> x.hexdigest() 
'acbd18db4cc2f85cedef654fccc4a4d8' 

[Editar]: Se ha actualizado para utilizar mejor método (códec hex)

+1

En la primera versión, ¿hay algo especial que importar para utilizar la declaración del grupo? –

+0

@Leandro: Oops - group() era una función en mi propia biblioteca (divide una secuencia en grupos de N caracteres). Actualicé el código para usar solo una porción para evitar la función indefinida. – Brian

Cuestiones relacionadas