moduł struct w Pythonie

The moduł struktury W Pyton umożliwia pracę z danymi binarnymi, zapewniając funkcjonalność konwersji pomiędzy wartościami Pythona i danymi binarnymi w stylu C. Jest to szczególnie przydatne w przypadku binarnych formatów plików lub protokołów sieciowych. Jego najważniejsze cechy obejmują:

  • Uszczelka
  • Rozpakowywanie konwertuj dane binarne z powrotem na wartości Pythona.
  • Formatuj ciągi zdefiniuj sposób pakowania/rozpakowywania danych za pomocą kodów formatu (np. i dla liczb całkowitych f dla zmiennoprzecinkowych).

Metody w struct.pack()

1.Struct.pack(): Konwertuje wartości Pythona na spakowany format binarny. Ciąg formatujący (fmt) określa układ spakowanych danych, a kolejne wartości (v1 v2 ...) są pakowane zgodnie z tym formatem. Składnia:

struct.pack(fmt v1 v2 ...)

  • fmt : Ciąg formatujący określający sposób pakowania danych.
  • v1 v2...: Wartości, które zostaną spakowane zgodnie z określonym formatem.
Python
   import   struct   # pack values into binary   var   =   struct  .  pack  (  'hhl'     1     2     3  )   print  (  var  )   var   =   struct  .  pack  (  'iii'     1     2     3  )   print  (  var  )   

Wyjście
b'x01x00x02x00x00x00x00x00x03x00x00x00x00x00x00x00' b'x01x00x00x00x02x00x00x00x03x00x00x00'  

Wyjaśnienie: „hhl” oznacza dwie krótkie liczby całkowite (h 2 bajty każda), po których następuje długa (l zwykle 4 lub 8 bajtów w zależności od platformy). „iii” pakuje trzy 4-bajtowe liczby całkowite. Dane wyjściowe są wyrażone w bajtach (b'') reprezentujących kodowanie binarne wartości.

2.struktura.rozpakuj(): Konwertuje spakowane dane binarne z powrotem na wartości Pythona. Pobiera ciąg formatujący (fmt) i spakowany ciąg binarny i zwraca krotkę rozpakowanych wartości. Składnia:

struct.unpack(ciąg fmt)

  • fmt: Ciąg formatu określający sposób rozpakowywania danych.
  • smyczkowy: Spakowane dane binarne, które należy rozpakować.
Python
   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  )   

Wyjście
b'x01x00x02x00x05x00x00x00xbdx01x00x00x00x00x00x00' (True 2 5 445) b'x05x00x00x00x00x00x00x0033x13@' (5 2.299999952316284)  

Wyjaśnienie: W tym przykładzie najpierw pakowana jest wartość logiczna (?), krótka (h), liczba całkowita (i) i długa (l) w bajty. Następnie używana jest funkcja struct.unpack() do konwersji go z powrotem na wartości Pythona. Druga część pakuje długą, długą liczbę całkowitą (q) i liczbę zmiennoprzecinkową (f), a następnie rozpakowuje je z powrotem. Zwróć uwagę, że 2,3 staje się 2,299999952... ze względu na precyzję zmiennoprzecinkową.

3. struktura.calcsize(): Zwraca rozmiar (w bajtach) struktury odpowiadającej ciągowi formatującemu. Jest to pomocne przy określaniu, ile miejsca jest wymagane do przechowywania spakowanych danych. Składnia:

struct.calcsize(fmt)

  • fmt: Ciąg formatujący określający układ danych.
Python
   import   struct   print  (  struct  .  calcsize  (  '?hil'  ))   print  (  struct  .  calcsize  (  'qf'  ))   

Wyjście
16 12  

Wyjaśnienie: „?hil” wymaga 16 bajtów i „qf” potrzebuje 12 bajtów w zależności od wyrównania i platformy.

4. struct.pack_into() i struct.unpack_from(): Metody te umożliwiają bezpośrednie pakowanie i rozpakowywanie danych do/z bufora, zaczynając od danego przesunięcia. Są one szczególnie przydatne, gdy mamy do czynienia ze wstępnie przydzielonymi buforami pamięci lub podczas pracy z danymi binarnymi przechowywanymi w pamięci.

Składnia struct.pack_into():

struct.pack_into(przesunięcie bufora fmt v1 v2 ...)

  • fmt: Ciąg formatujący określający układ danych.
  • bufor: zapisywalny bufor (np. ctypes.create_string_buffer).
  • offset: Pozycja początkowa w buforze, w której rozpoczyna się pakowanie.
  • v1 v2 ...: Wartości, które mają zostać spakowane do bufora.

Składnia dla struct.unpack_from():

struct.unpack_from(przesunięcie bufora fmt=0)

  • fmt: Ciąg formatujący określający układ danych.
  • bufor: Bufor zawierający spakowane dane.
  • zrównoważyć: Pozycja wyjściowa, od której rozpoczyna się rozpakowywanie (opcjonalnie)
Python
   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  )   

Wyjście
(2 2 3)  

Wyjaśnienie: Tutaj tworzony jest bufor za pomocą ctypes. struktura.pack_into() wstawia wartości do tego bufora z określonym przesunięciem (w tym przypadku 0). struktura.rozpakuj_z() następnie odczytuje dane z bufora.

Wpływ kolejności formatów

Kolejność znaków formatu może zmienić spakowane dane wyjściowe z powodu dopełnienia i wyrównania. Ma to wpływ zarówno na zawartość bajtów, jak i rozmiar wyniku.

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'  ))   

Wyjście
b'8x00x00x00x15x14x13x12' 8 b'x15x14x13x128' 5  

Objaśnienie: „bi” (bajt int) może zawierać dopełnienie po bajcie, podczas gdy „ib” (int bajt) nie potrzebuje tego. Różnica wielkości (8 vs 5) pokazuje, jak wyrównanie wpływa na układ pamięci.

Obsługa błędów

Jeśli w struct.pack() zostanie użyty niewłaściwy typ danych, wystąpi błąd struct. Użyj try-except, aby bezpiecznie obsługiwać takie przypadki.

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  }  '  )   

Wyjście

 Struct Error: required argument is not an integer   

Wyjaśnienie: To pokazuje obsługę błędów podczas używania struktury. „h” oczekuje krótkiej liczby całkowitej, ale podano ciąg znaków („nieprawidłowy”), powodując błąd struktury. Blok try-except przechwytuje błąd i wyświetla znaczący komunikat.

Odniesienie https://docs.python.org/2/library/struct.html

Utwórz quiz