struct modul v Pythonu
The struct modul v Python vam omogoča delo z binarnimi podatki z zagotavljanjem funkcionalnosti za pretvorbo med vrednostmi Python in binarnimi podatki v slogu C. To je še posebej uporabno pri delu z binarnimi oblikami datotek ali omrežnimi protokoli. Njegove ključne značilnosti vključujejo:
- Pakiranje pretvori vrednosti Python v binarne podatke (bajte).
- Razpakiranje pretvorite binarne podatke nazaj v vrednosti Python.
- Oblikuj nize določite, kako se podatki zapakirajo/razpakirajo z uporabo kod formatov (npr. i za cela števila f za lebdeče).
Metode v struct.pack()
1.Struct.pack(): Vrednosti Python pretvori v zapakirano binarno obliko. Niz formata (fmt) določa postavitev pakiranih podatkov in naslednje vrednosti (v1 v2 ...) so pakirane v skladu s tem formatom. Sintaksa:
struct.pack(fmt v1 v2 ...)
- fmt : formatni niz, ki določa, kako bodo podatki pakirani.
- v1 v2 ...: Vrednosti, ki bodo zapakirane v skladu s podanim formatom.
import struct # pack values into binary var = struct . pack ( 'hhl' 1 2 3 ) print ( var ) var = struct . pack ( 'iii' 1 2 3 ) print ( var )
Izhod
b'x01x00x02x00x00x00x00x00x03x00x00x00x00x00x00x00' b'x01x00x00x00x02x00x00x00x03x00x00x00'
Pojasnilo: 'hhl' pomeni dve kratki celi števili (h 2 bajta vsako), ki jima sledi dolgo (l običajno 4 ali 8 bajtov, odvisno od platforme). 'iii' pakira tri 4-bajtna cela števila. Izhod je v bajtih (b''), ki predstavljajo binarno kodiranje vrednosti.
2.struct.unpack(): Pakirane binarne podatke pretvori nazaj v vrednosti Python. Vzame formatni niz (fmt) in zapakiran binarni niz ter vrne zbirko nepakiranih vrednosti. Sintaksa:
struct.unpack(fmt niz)
- fmt: Oblikovni niz, ki določa, kako naj bodo podatki razpakirani.
- niz: Pakirani binarni podatki, ki jih je treba razpakirati.
import struct var = struct . pack ( '?hil' True 2 5 445 ) print ( var ) tup = struct . unpack ( '?hil' var ) print ( tup ) var = struct . pack ( 'qf' 5 2.3 ) print ( var ) tup = struct . unpack ( 'qf' var ) print ( tup )
Izhod
b'x01x00x02x00x05x00x00x00xbdx01x00x00x00x00x00x00' (True 2 5 445) b'x05x00x00x00x00x00x00x0033x13@' (5 2.299999952316284)
Pojasnilo: Ta primer najprej zapakira logično vrednost (?), kratko (h), celo število (i) in dolgo (l) v bajte. Nato se struct.unpack() uporabi za pretvorbo nazaj v vrednosti Python. Drugi del pakira dolgo dolgo celo število (q) in plavajočo oznako (f), nato pa ju razpakira nazaj. Upoštevajte, kako 2,3 postane 2,299999952 ... zaradi natančnosti float.
3. struct.calcsize(): Vrne velikost (v bajtih) strukture, ki ustreza formatnemu nizu. V pomoč je pri določanju, koliko prostora je potrebno za shranjevanje pakiranih podatkov. Sintaksa:
struct.calcsize(fmt)
- fmt: formatni niz, ki določa postavitev podatkov.
import struct print ( struct . calcsize ( '?hil' )) print ( struct . calcsize ( 'qf' ))
Izhod
16 12
Pojasnilo: '?hil' zahteva 16 bajtov in 'qf' potrebuje 12 bajtov, odvisno od poravnave in platforme.
4. struct.pack_into() in struct.unpack_from(): Te metode vam omogočajo neposredno pakiranje in razpakiranje podatkov v medpomnilnik/iz njega, začenši z danim odmikom. To je še posebej uporabno pri delu z vnaprej dodeljenimi medpomnilniki ali pri delu z binarnimi podatki, shranjenimi v pomnilniku.
Sintaksa za struct.pack_into():
struct.pack_into(fmt medpomnilnik odmik v1 v2 ...)
- fmt: formatni niz, ki določa postavitev podatkov.
- medpomnilnik: zapisljivi medpomnilnik (npr. ctypes.create_string_buffer).
- odmik: začetni položaj v medpomnilniku, kjer se začne pakiranje.
- v1 v2 ...: Vrednosti, ki jih je treba zapakirati v medpomnilnik.
Sintaksa za struct.unpack_from():
struct.unpack_from(fmt medpomnilnik=0)
- fmt: Oblikovni niz, ki določa postavitev podatkov.
- medpomnilnik: Medpomnilnik, ki vsebuje zapakirane podatke.
- odmik: Začetni položaj, od koder se začne razpakiranje (neobvezno)
import struct import ctypes # Allocate buffer size = struct . calcsize ( 'hhl' ) buff = ctypes . create_string_buffer ( size ) # Pack into buffer struct . pack_into ( 'hhl' buff 0 2 2 3 ) # Unpack from buffer res = struct . unpack_from ( 'hhl' buff 0 ) print ( res )
Izhod
(2 2 3)
Pojasnilo: Tukaj je medpomnilnik ustvarjen z uporabo ctypes. struct.pack_into() vstavi vrednosti v ta medpomnilnik pri podanem odmiku (0 v tem primeru). struct.unpack_from() nato prebere podatke nazaj iz medpomnilnika.
Učinek vrstnega reda formata
Vrstni red formatnih znakov lahko spremeni pakirani izpis zaradi oblazinjenja in poravnave. To vpliva tako na vsebino bajtov kot na velikost rezultata.
Python import struct var = struct . pack ( 'bi' 56 0x12131415 ) print ( var ) print ( struct . calcsize ( 'bi' )) var = struct . pack ( 'ib' 0x12131415 56 ) print ( var ) print ( struct . calcsize ( 'ib' ))
Izhod
b'8x00x00x00x15x14x13x12' 8 b'x15x14x13x128' 5
Pojasnilo: 'bi' (bajt int) lahko vključuje oblazinjenje za bajtom, medtem ko 'ib' (int bajt) ga ne potrebuje. Razlika v velikosti (8 proti 5) kaže, kako poravnava vpliva na postavitev pomnilnika.
Napake pri ravnanju
Če je s struct.pack() uporabljen napačen podatkovni tip, pride do struct.error. Za varno obravnavo takih primerov uporabite poskusi-razen.
Python import struct try : struct . pack ( 'h' 'invalid' ) # Wrong type 'invalid' is a string but 'h' expects an integer except struct . error as e : print ( f 'Struct Error: { e } ' )
Izhod
Struct Error: required argument is not an integer
Pojasnilo: To prikazuje obravnavo napak pri uporabi struct. 'h' pričakuje kratko celo število, vendar je podan niz ('neveljaven'), ki povzroči struct.error. Blok poskusi razen zajame napako in natisne smiselno sporočilo.
Referenca https://docs.python.org/2/library/struct.html
Ustvari kviz