Python 模塊 Pickle

Python 模塊 Pickle

pickle 模塊的目的是對象的序列化(Object serialization)。

pickle 模塊實現了一個算法,能把任何一個對象轉變為一串字節流,這個過程就叫對象的序列化

(serializing the object)。生成的字節流可以傳輸和保存,還能重新生成一個對象。

當解析一個未知的字節流時,可能是危險的,因為它可能是任何代碼。尤其是跨進程通信的程序,需要驗證這種安全性,例如可以使用 hmac 模塊為數據源進行簽名,然後反序列化為對象之前,首先驗證這個簽名是否正確。

編碼和解碼數據 Encoding and Decoding


dumps() 方法可以把 Python 的一個內置數據類型的數據編碼為字節流。

Python 模塊 Pickle

執行:

Python 模塊 Pickle

dumps() 方法返回的是一串字節流,它可以寫進一個文件(File),套接字(Socket)和管道

(Pipe)等等。又可以重新生成一個對象。

Python 模塊 Pickle

執行:

Python 模塊 Pickle

可以看到,使用 loads() 函數從字節流生成的對象和之前的一樣。

寫入文件流(file-like streams)


除了方法 dumps() 和 loads() 外,還可以直接將對象寫入到一個類文件流(file-like streams)中。然後還可以從類文件流中讀取出來,可多次寫入和讀取。

使用的方法是 dump() 和 load() ,和上面的方法很像,少了個字母 s。

Python 模塊 Pickle

執行:

Python 模塊 Pickle

這個例子,首先使用 io 模塊生成了一個二進制流 f,然後使用 dump() 方法分別把2個 A 對象寫入到流 f 中。

然後從被寫入的流中使用函數 getvalue() 獲取值,構建一個輸入流 f_input,用一個 while 無限循環分別使用 load() 方法從輸入流加載對象,直到2個對象加載完成後,觸發異常

EOFError 退出。

pickle 模塊常用在進程間通信(inter-process communication)的應用,例如使用 os.fork() 和 os.pipe() 生成的進程和管道,從一個進程或管道讀取數據,然後流向另一個

進程或管道。別忘了 dump() 之後,一定要執行 flush() 方法,把數據流推送給對方。

不可序列化的對象


不是所有的對象都是可以 pickle 的,例如套接字(Sockets)、文件描述符(file handles)、數據庫連接(database connections)或者其他對象依賴於操作系統或者其他進程的。

這種不能 pickle 的對象可以定義 __getstate__() 和 __setstate__() 方法。

__getstate__() 在序列化的時候調用,必須返回一個可 pickle 的對象記錄自身的狀態,可以是自定義的對象或者是內置的數據類型如字典。

__setstate__() 方法是在從 pickle 數據反序列化時調用的。參數是 __getstate__() 返回的數據類型值。

Python 模塊 Pickle

執行:

Python 模塊 Pickle

這個例子中,序列化的時候,調用 __getstate__() 方法返回一個字典對象記錄自身的狀態。反序列化時,把值傳入了 __setstate__() 方法。


分享到:


相關文章: