deflate — komprese a dekomprese deflate¶
Tento modul umožňuje kompresi a dekompresi binárních dat pomocí algoritmu DEFLATE (běžně používaného v knihovně zlib a archivátoru gzip). Přidáno v MicroPythonu v1.21.
Dostupnost na deskách podporovaných OpenMV:
Deska |
Dekomprese |
Komprese |
|---|---|---|
OpenMV Cam N6 |
Ano |
Ne |
OpenMV AE3 |
Ano |
Ano |
OpenMV Cam RT1062 |
Ano |
Ano |
OpenMV Cam Pure Thermal |
Ano |
Ne |
OpenMV Cam M4 |
Ano |
Ne |
OpenMV Cam M7 |
Ano |
Ne |
OpenMV Cam H7 |
Ano |
Ne |
OpenMV Cam H7 Plus |
Ano |
Ne |
Arduino Giga |
Ano |
Ne |
Arduino Portenta H7 |
Ano |
Ne |
Arduino Nicla Vision |
Ano |
Ne |
Arduino Nano 33 BLE Sense |
Ano |
Ne |
Arduino Nano RP2040 Connect |
Ano |
Ne |
Třídy¶
- class deflate.DeflateIO(stream: Any, format: int = AUTO, wbits: int = 0, close: bool = False, /)¶
Tuto třídu lze použít k zabalení stream objektu, což je libovolný objekt podobný streamu, jako je soubor, socket nebo stream (včetně
io.BytesIO). Sama je streamem a implementuje standardní metody read/readinto/write/close.stream musí být blokující stream. Neblokující streamy nejsou momentálně podporovány.
format lze nastavit na libovolnou z konstant definovaných níže a výchozí hodnota je
AUTO, která při dekompresi automaticky detekuje streamy gzip nebo zlib a při kompresi generuje surový stream.Parametr wbits nastavuje dvojkový logaritmus velikosti okna slovníku DEFLATE. Například nastavení wbits na
10nastaví velikost okna na 1024 bajtů. Platné hodnoty jsou5až15včetně (odpovídající velikostem okna 32 až 32k bajtů).Pokud je wbits nastaveno na
0(výchozí), pak se pro kompresi použije velikost okna 256 bajtů (jako by bylo wbits nastaveno na 8). Pro dekompresi to závisí na formátu:RAWpoužije 256 bajtů (odpovídá wbits nastavenému na 8).ZLIB(neboAUTOs detekovaným zlib) použije hodnotu z hlavičky zlib.GZIP(neboAUTOs detekovaným gzip) použije 32 kilobajtů (odpovídá wbits nastavenému na 15).
Více informací o velikosti okna, streamech zlib a gzip najdete v poznámkách o velikosti okna níže.
Pokud je close nastaveno na
True, pak se podkladový stream automaticky uzavře při uzavření streamudeflate.DeflateIO. To je užitečné, pokud chcete vrátit streamdeflate.DeflateIO, který zabaluje jiný stream, a nechcete, aby se volající musel starat o správu podkladového streamu.Pokud je povolena komprese, daná instance
deflate.DeflateIOpodporuje jak čtení, tak zápis. Lze například zabalit obousměrný stream, jako je socket, což umožňuje kompresi/dekompresi v obou směrech.
Konstanty¶
Čtyři konstanty format volí rámcování aplikované kolem surového bitového streamu deflate.
- deflate.AUTO: int¶
Pro dekompresi automaticky detekuje vstupní formát prozkoumáním prvních bajtů streamu (zlib nebo gzip). Pro kompresi generuje surový stream deflate bez hlavičky a koncové části (ekvivalent
RAW).
- deflate.RAW: int¶
Surový stream deflate (bez hlavičky, bez koncové části, bez kontrolního součtu). Protože stream neobsahuje žádná metadata, dekompresor nemůže obnovit velikost okna z dat, takže wbits by mělo být při dekompresi nastaveno explicitně – jinak může být výchozí 256bajtové okno příliš malé.
- deflate.ZLIB: int¶
Stream deflate zabalený do zlib, jak je definováno v RFC 1950: 2bajtová hlavička, která zaznamenává velikost okna, datová část deflate a koncový kontrolní součet Adler-32. Kompaktní a sebepopisující; dobře se hodí pro vestavěné použití.
- deflate.GZIP: int¶
Stream deflate zabalený do gzip, jak je definováno v RFC 1952: hlavička s volitelnými metadaty názvu souboru/časové značky, datová část deflate a koncový kontrolní součet CRC-32 plus nekomprimovaná délka. Toto je formát produkovaný nástrojem příkazové řádky
gzipa třídougzip.GzipFile. Hlavička nezaznamenává velikost okna, takže dekompresor musí předpokládat 32 KiB, pokud není nastaveno wbits.
Příklady¶
Typickým případem použití deflate.DeflateIO je čtení nebo zápis komprimovaného souboru z úložiště:
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.
Protože deflate.DeflateIO je stream, lze jej použít například s json.dump() a json.load() (a kdekoli jinde, kde lze použít streamy):
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)
Pokud vaše zdrojová data nejsou ve formátu streamu, můžete použít io.BytesIO k jejich převedení na stream vhodný pro použití s 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()
Velikost okna deflate¶
Velikost okna omezuje, jak daleko zpět ve streamu může (de)kompresor odkazovat. Zvětšení velikosti okna zlepší kompresi, ale bude vyžadovat více paměti a zpomalí kompresor.
Pokud byl vstupní stream komprimován s danou velikostí okna, pak DeflateIO používající menší velikost okna selže uprostřed dekomprese s OSError, ale pouze tehdy, pokud zpětný odkaz skutečně odkazuje dále zpět, než je velikost okna dekompresoru. To znamená, že může být možné dekomprimovat s menší velikostí okna. To by například triviálně platilo, pokud jsou původní nekomprimovaná data kratší než velikost okna.
Dekomprese¶
Formát zlib obsahuje hlavičku, která určuje velikost okna použitou ke kompresi dat. To udává maximální velikost okna potřebnou k dekompresi tohoto streamu. Pokud je tato hodnota z hlavičky menší než zadaná hodnota wbits (nebo pokud wbits není nastaveno), pak se použije hodnota z hlavičky.
Formát gzip nezahrnuje velikost okna v hlavičce a předpokládá, že všechny kompresory gzip (např. nástroj gzip nebo implementace gzip.GzipFile v CPythonu) používají maximální velikost okna 32 KiB. Z tohoto důvodu, pokud parametr wbits není nastaven, dekompresor použije velikost okna 32 KiB (odpovídá wbits nastavenému na 15). To znamená, že abyste mohli dekomprimovat libovolný stream gzip, musíte mít k dispozici alespoň tolik paměti RAM. Pokud máte kontrolu nad zdrojovými daty, zvažte raději použití formátu zlib s menší velikostí okna.
Surový formát nemá žádnou hlavičku, a proto neobsahuje žádné informace o velikosti okna. Pokud wbits není nastaveno, pak se použije výchozí velikost okna 256 bajtů, která nemusí být pro daný stream dostatečně velká. Proto se doporučuje vždy explicitně nastavit wbits při použití surového formátu.
Komprese¶
Pro kompresi MicroPython použije výchozí velikost okna 256 bajtů pro všechny formáty. To poskytuje rozumnou míru komprese s minimálním využitím paměti a rychlou dobou komprese a generuje výstup, který bude fungovat s libovolným dekompresorem.