Python multiprocess pool模塊報錯pickling error問題解決方法分析

這篇文章主要介紹了Python multiprocess pool模塊報錯pickling error問題解決方法,結合實例形式分析了multiprocess pool模塊報錯pickling error的原因與解決方法,需要的朋友可以參考下

本文實例講述了Python multiprocess pool模塊報錯pickling error問題解決方法。分享給大家供大家參考,具體如下:

問題

之前在調用class內的函數用multiprocessing模塊的pool函數進行多線程處理的時候報了以下下錯誤信息:

PicklingError: Can't pickle <type 'function'>: attribute lookup __builtin__.function failed

查了下官方文檔發現python默認只能pickle以下的類型:

  • None, True, and False
  • integers, floating point numbers, complex numbers
  • strings, bytes, bytearrays
  • tuples, lists, sets, and dictionaries containing only picklable objects
  • functions defined at the top level of a module (using def, not lambda)
  • built-in functions defined at the top level of a module
  • classes that are defined at the top level of a module
  • instances of such classes whose dict or the result of calling getstate() is picklable (see section -
  • Pickling Class Instances for details).

函數只能pickle在頂層定義的函數,很明顯的class內的函數無法被pickle因此會報錯。

import multiprocessing
def work():  # top-level 函數
  print "work!"
class Foo():
  def work(self): # 非top-level函數
    print "work"
pool1 = multiprocessing.Pool(processes=4)
foo = Foo()
pool1.apply_async(foo.work)
pool1.close()
pool1.join()
# 此時報錯
pool2 = multiprocessing.Pool(processes=4)
pool2.apply_async(work)
pool2.close()
pool2.join()
# 此時工作正常

解決方案

調用pathos包下的multiprocessing模塊代替原生的multiprocessing。pathos中multiprocessing是用dill包改寫過的,dill包可以將幾乎所有python的類型都serialize,因此都可以被pickle。或者也可以自己用dill寫一個(有點重複造輪子之嫌啊)

參考

1. https://stackoverflow.com/questions/8804830/python-multiprocessing-picklingerror-cant-pickle-type-function
2. https://docs.python.org/3/library/pickle.html#what-can-be-pickled-and-unpickled
3. https://github.com/uqfoundation/pathos

更多關於Python相關內容感興趣的讀者可查看本站專題:《Python進程與線程操作技巧總結》、《Python數據結構與算法教程》、《Python函數使用技巧總結》、《Python字符串操作技巧彙總》、《Python入門與進階經典教程》、《Python+MySQL數據庫程序設計入門教程》及《Python常見數據庫操作技巧彙總

希望本文所述對大家Python程序設計有所幫助。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章