deflate — compressione e decompressione deflate¶
Questo modulo consente la compressione e la decompressione di dati binari con l”algoritmo DEFLATE (comunemente usato nella libreria zlib e nell’archiviatore gzip). Aggiunto in MicroPython v1.21.
Disponibilità sulle schede supportate da OpenMV:
Scheda |
Decompressione |
Compressione |
|---|---|---|
OpenMV Cam N6 |
Sì |
No |
OpenMV AE3 |
Sì |
Sì |
OpenMV Cam RT1062 |
Sì |
Sì |
OpenMV Cam Pure Thermal |
Sì |
No |
OpenMV Cam M4 |
Sì |
No |
OpenMV Cam M7 |
Sì |
No |
OpenMV Cam H7 |
Sì |
No |
OpenMV Cam H7 Plus |
Sì |
No |
Arduino Giga |
Sì |
No |
Arduino Portenta H7 |
Sì |
No |
Arduino Nicla Vision |
Sì |
No |
Arduino Nano 33 BLE Sense |
Sì |
No |
Arduino Nano RP2040 Connect |
Sì |
No |
Classi¶
- class deflate.DeflateIO(stream: Any, format: int = AUTO, wbits: int = 0, close: bool = False, /)¶
Questa classe può essere usata per incapsulare uno stream che è un qualsiasi oggetto simile a uno stream come un file, un socket o uno stream (incluso
io.BytesIO). È essa stessa uno stream e implementa i metodi standard read/readinto/write/close.Lo stream deve essere uno stream bloccante. Gli stream non bloccanti attualmente non sono supportati.
Il parametro format può essere impostato a una qualsiasi delle costanti definite di seguito, e il valore predefinito è
AUTOche per la decompressione rileverà automaticamente gli stream gzip o zlib, mentre per la compressione genererà uno stream raw.Il parametro wbits imposta il logaritmo in base 2 della dimensione della finestra del dizionario DEFLATE. Quindi, per esempio, impostando wbits a
10si imposta la dimensione della finestra a 1024 byte. I valori validi vanno da5a15inclusi (corrispondenti a dimensioni della finestra da 32 a 32k byte).Se wbits è impostato a
0(il valore predefinito), allora per la compressione verrà usata una dimensione della finestra di 256 byte (come se wbits fosse impostato a 8). Per la decompressione, dipende dal formato:RAWuserà 256 byte (corrispondenti a wbits impostato a 8).ZLIB(oAUTOcon zlib rilevato) userà il valore dell’header zlib.GZIP(oAUTOcon gzip rilevato) userà 32 kilobyte (corrispondenti a wbits impostato a 15).
Vedi le note sulla dimensione della finestra più avanti per maggiori informazioni sulla dimensione della finestra e sugli stream zlib e gzip.
Se close è impostato a
Trueallora lo stream sottostante verrà chiuso automaticamente quando lo streamdeflate.DeflateIOviene chiuso. Questo è utile se vuoi restituire uno streamdeflate.DeflateIOche incapsula un altro stream senza che il chiamante debba preoccuparsi di gestire lo stream sottostante.Se la compressione è abilitata, una data istanza
deflate.DeflateIOsupporta sia la lettura che la scrittura. Per esempio, è possibile incapsulare uno stream bidirezionale come un socket, il che consente la compressione/decompressione in entrambe le direzioni.
Costanti¶
Le quattro costanti format selezionano l’incapsulamento applicato attorno al bit-stream deflate grezzo.
- deflate.AUTO: int¶
Per la decompressione, rileva automaticamente il formato dell’input ispezionando i primi byte dello stream (zlib o gzip). Per la compressione, genera uno stream deflate grezzo senza header né trailer (equivalente a
RAW).
- deflate.RAW: int¶
Uno stream deflate grezzo (nessun header, nessun trailer, nessun checksum). Poiché lo stream non contiene metadati, il decompressore non può recuperare la dimensione della finestra dai dati, quindi wbits dovrebbe essere impostato esplicitamente durante la decompressione — altrimenti la finestra predefinita di 256 byte potrebbe essere troppo piccola.
- deflate.ZLIB: int¶
Uno stream deflate incapsulato in zlib come definito da RFC 1950: un header di 2 byte che registra la dimensione della finestra, il payload deflate e un checksum Adler-32 finale. Compatto e auto-descrittivo; ben adatto all’uso in ambito embedded.
- deflate.GZIP: int¶
Uno stream deflate incapsulato in gzip come definito da RFC 1952: un header con metadati opzionali di nome file/timestamp, il payload deflate e un CRC-32 finale più la lunghezza non compressa. Questo è il formato prodotto dallo strumento da riga di comando
gzipe dagzip.GzipFile. L’header non registra la dimensione della finestra, quindi il decompressore deve assumere 32 KiB a meno che wbits non sia impostato.
Esempi¶
Un caso d’uso tipico di deflate.DeflateIO è leggere o scrivere un file compresso dalla memoria:
import deflate
# Writing a zlib-compressed stream (uses the default window size of 256 bytes).
with open("data.z", "wb") as f:
with deflate.DeflateIO(f, deflate.ZLIB) as d:
# Use d.write(...) etc
# Reading a zlib-compressed stream (auto-detect window size).
with open("data.z", "rb") as f:
with deflate.DeflateIO(f, deflate.ZLIB) as d:
# Use d.read(), d.readinto(), etc.
Poiché deflate.DeflateIO è uno stream, può essere usato per esempio con json.dump() e json.load() (e in qualsiasi altro punto in cui possono essere usati gli stream):
import deflate, json
# Write a dictionary as JSON in gzip format, with a
# small (64 byte) window size.
config = { ... }
with open("config.gz", "wb") as f:
with deflate.DeflateIO(f, deflate.GZIP, 6) as f:
json.dump(config, f)
# Read back that dictionary.
with open("config.gz", "rb") as f:
with deflate.DeflateIO(f, deflate.GZIP, 6) as f:
config = json.load(f)
Se i tuoi dati di origine non sono in formato stream, puoi usare io.BytesIO per trasformarli in uno stream adatto all’uso con deflate.DeflateIO:
import deflate, io
# Decompress a bytes/bytearray value.
compressed_data = get_data_z()
with deflate.DeflateIO(io.BytesIO(compressed_data), deflate.ZLIB) as d:
decompressed_data = d.read()
# Compress a bytes/bytearray value.
uncompressed_data = get_data()
stream = io.BytesIO()
with deflate.DeflateIO(stream, deflate.ZLIB) as d:
d.write(uncompressed_data)
compressed_data = stream.getvalue()
Dimensione della finestra deflate¶
La dimensione della finestra limita quanto indietro nello stream il (de)compressore può fare riferimento. Aumentare la dimensione della finestra migliorerà la compressione, ma richiederà più memoria e renderà il compressore più lento.
Se uno stream di input è stato compresso con una data dimensione della finestra, allora DeflateIO che usa una dimensione della finestra più piccola fallirà a metà durante la decompressione con OSError, ma solo se un riferimento all’indietro fa effettivamente riferimento più indietro rispetto alla dimensione della finestra del decompressore. Ciò significa che potrebbe essere possibile decomprimere con una dimensione della finestra più piccola. Per esempio, questo sarebbe banalmente vero se i dati originali non compressi fossero più corti della dimensione della finestra.
Decompressione¶
Il formato zlib include un header che specifica la dimensione della finestra usata per comprimere i dati. Questo indica la dimensione massima della finestra richiesta per decomprimere questo stream. Se questo valore dell’header è inferiore al valore wbits specificato (o se wbits non è impostato), verrà usato il valore dell’header.
Il formato gzip non include la dimensione della finestra nell’header e presume che tutti i compressori gzip (ad esempio l’utilità gzip o l’implementazione di gzip.GzipFile di CPython) usino la dimensione massima della finestra di 32 kiB. Per questo motivo, se il parametro wbits non è impostato, il decompressore userà una dimensione della finestra di 32 kiB (corrispondente a wbits impostato a 15). Ciò significa che per poter decomprimere uno stream gzip arbitrario devi disporre almeno di questa quantità di RAM. Se controlli i dati di origine, considera invece l’uso del formato zlib con una dimensione della finestra più piccola.
Il formato raw non ha header e quindi non include alcuna informazione sulla dimensione della finestra. Se wbits non è impostato, assumerà come valore predefinito una dimensione della finestra di 256 byte, che potrebbe non essere abbastanza grande per un dato stream. Pertanto si raccomanda di impostare sempre esplicitamente wbits quando si usa il formato raw.
Compressione¶
Per la compressione, MicroPython userà come valore predefinito una dimensione della finestra di 256 byte per tutti i formati. Questo fornisce una quantità ragionevole di compressione con un utilizzo minimo di memoria e tempi di compressione rapidi, e genererà un output che funzionerà con qualsiasi decompressore.