Contenido
- 1. Uso del módulo struct. Datos binarios empaquetados
- 2. Los métodos básicos del módulo struct
- 2.1. Los métodos pack() y unpack(). Empaquetar y desempaquetar datos
- 2.2. Método calcsize(). El tamaño del objeto empaquetado
- 3. Cadenas formateadas
- 3.1. Establecer el orden de los bytes, el tamaño y la alineación en función del carácter de formato
- 3.2. Ejemplos de cadenas formateadas para diferentes tipos de datos
- Temas relacionados
Busca en otros sitios web:
1. Uso del módulo struct. Datos binarios empaquetados
El módulo struct de Python se utiliza para crear y extraer datos binarios empaquetados de cadenas. En el módulo struct, los bytes de datos se interpretan como datos binarios empaquetados que pueden representarse mediante objetos de tipo bytes o bytearray.
El módulo contiene herramientas de conversión entre valores de Python y estructuras de C, que se representan como objetos byte de Python. Dichas conversiones se utilizan en el procesamiento de datos binarios que se almacenan en archivos o se obtienen de conexiones de red, etc.
Para proporcionar una descripción compacta de las estructuras C y la conversión a valores (desde valores) de Python, se utilizan cadenas de formato.
⇑
2. Los métodos básicos del módulo struct
El módulo struct contiene varios métodos básicos que puede utilizar para empaquetar y desempaquetar datos.
2.1. Los métodos pack() y unpack(). Empaquetar y desempaquetar datos
Para empaquetar y desempaquetar datos, se utilizan los métodos pack(), unpack(). El proceso de empaquetado/desempaquetado se implementa de acuerdo con la cadena de formato.
De acuerdo con la documentación, la forma general de utilizar el método pack() es la siguiente
obj = struct.pack(format, v1, v2, ...)
donde
- format – cadena de formato. Esta cadena se forma según las reglas establecidas en las tablas (ver apartado 3);
- v1, v2, … – valores (objetos) a empaquetar;
- obj – objeto binario empaquetado.
La función unpack() realiza la operación inversa a la de pack(). Permite obtener el objeto fuente a partir del objeto empaquetado. La forma general de utilizar la función es la siguiente:
obj = struct.unpack(format, buffer)
aquí
- buffer – un buffer en el que se escribe un objeto que fue previamente empaquetado por la función pack(). El tamaño de este objeto debe coincidir con el tamaño especificado en format;
- format – una cadena de formato en base a la cual se obtiene un objeto binario desempaquetado obj;
- obj – el objeto resultante, que puede ser una lista, una tupla, un conjunto, un diccionario, etc.
Cuando se llama a la función unpack(), la cadena de formato debe coincidir con la misma cadena que fue especificada por la función pack().
Ejemplo. A efectos de demostración, se realiza el empaquetado/desempaquetado de la lista de números.
# Module struct. Methods pack(), unpack()# Pack/unpack list of numbers# 1. Specified list of numbersLS = # 2. Include module structimport struct# 3. Pack list of numbers. Method pack()pack_obj = struct.pack('>4і', LS, LS, LS, LS)# 4. Display the object pack_objprint('pack_obj = ', pack_obj)# 5. Unpack list of numbers. Method unpack().# The result is a tuple T2T2 = struct.unpack('>4і', pack_obj) # T2 = (1, 3, 9, 12)# 6. Print the unpacked object T2print('T2 = ', T2)# 7. Convert tuple T2 to list LS2LS2 = list(T2) # LS2 = # 8. Display the list LS2print('LS2 = ', LS2)
El resultado del programa
pack_obj = b'\x00\x00\x00\x01\x00\x00\x00\x03\x00\x00\x00\t\x00\x00\x00\x0c'T2 = (1, 3, 9, 12)LS2 =
⇑
2.2. Método calcsize(). El tamaño del objeto empaquetado
El método calcsize() devuelve el tamaño del objeto creado por el método pack().
Ejemplo.
# Module struct.# Method calcsize(). Determine the size of the packed object# 1. Include module structimport struct# 2. Determine the size of a packed list of numbers# 2.1. Specified list of floating point numbersLS = # 2.2. Pack list LS. Method pack()pack_obj = struct.pack('>3f', LS, LS, LS)# 2.3. Display the packed object pack_objprint('pack_obj = ', pack_obj)# 2.4. Display the size of pack_objsize = struct.calcsize('>3f') # size = 12print('size = ', size)# 3. Determine the size of a packed tuple of strings# 3.1. The specified tuple of two stringsTS = ( 'Hello', 'abcd')# 3.2. Pack the tuple TSpack_obj = struct.pack('<5s4s', TS.encode(), TS.encode())# 3.3. Display the packed objectprint('pack_obj = ', pack_obj)# 3.4. Display the size of packed tuplesize = struct.calcsize('<5s4s') # size = 9print('size = ', size)
El resultado del programa
pack_obj = b'@8Q\xec@y\x99\x9a\xc1(\x00\x00'size = 12pack_obj = b'Helloabcd'size = 9
⇑
3. Cadenas formateadas
3.1. Establecer el orden de los bytes, el tamaño y la alineación en función del carácter de formato
En Python, la forma de empaquetar una cadena se determina en función del primer carácter de la cadena de formato. ¡Este símbolo define:
- el orden de los bytes, que se forma con los caracteres @, =, <>, ! Si no se especifica este parámetro, se acepta el símbolo @;
- el tamaño en bytes de los datos empaquetados. En este caso, se utilizan primero los números que indican el número;
- la alineación, que es establecida por el sistema.
- Orden nativo. Este orden puede ser little-endian o big-endian. Este orden está determinado por el sistema anfitrión;
- orden de tipo little-endian. En este orden, se procesa primero el byte bajo y luego el alto;
- orden de tipo big-endian. En este caso, se procesa primero el byte alto y luego el bajo;
- orden de red, que por defecto es el orden big-endian.
- natural – se define utilizando las instrucciones del compilador de C sizeof;
- estándar – se determina en base al carácter de formato de acuerdo con la siguiente tabla.
Según la documentación de Python en la cadena de formato, el orden de los bytes, el tamaño y la alineación se forman según el primer carácter del formato. Los posibles primeros caracteres del formato se muestran en la siguiente tabla.
Caracteres | Orden de los bytes | Tamaño | Alineación | @ | nativo (depende del host) | Nativo | Nativo |
= | nativo | estándar | ninguno |
< | little-endian | standard | none | > | big-¡endian | standard | none |
! | red (= big-endian) | standard | none |
Un valor de orden de bytes puede ser uno de 4:
El tamaño de los datos empaquetados puede ser una de estas dos cosas:
Tabla. Definición del tamaño estándar de los datos empaquetados en función del carácter de formato
Formato | Tipo C | Python Type | Tamaño estándar |
x | pad byte | sin valor | c | char | bytes de longitud 1 | 1 | b | signed char | integro | 1 |
B | unsigned char | integer | 1 |
? | _Bool | bool | 1 |
h | short | integer | 2 | H | unsigned short | integer | 2 |
i | int | integros | 4 |
I | unsigned int | integer | 4 |
l | long | integer | 4 |
L | unsigned long | integer | 4 |
q | long long | integer | 8 | Q | largo sin signo | integer | 8 |
n | ssize_t | integer | N | size_t | integer |
e | float (formato exponencial) | float | 2 |
f | float | float | 4 |
d | double | float | 8 | s | char | bytes | p | char | bytes |
P | void* | integer |