6

私はmultiprocessingモジュールを使用しており、プロセス間で通信するために、オブジェクトUpdateMessageを介して送信されるオブジェクト (自分のクラス)を使用していmultiprocessing.Queueます。クラスは次のとおりです。

class UpdateMessage:
    def __init__(self, arrayref, rowslice, colslice, newval):
        self.arrayref = arrayref
        self.rowslice = rowslice
        self.colslice = colslice
        self.newval = newval
    def do_update(self):
        if self.arrayref == 'uL':
            arr = uL
        elif self.arrayref == 'uR':
            arr = uR
        else:
            raise Exception('UpdateMessage.arrayref neither uL nor uR')
        arr[self.rowslice, self.colslice] = self.newval

スクリプトを実行すると、問題なく動作します。ただし、またはのいずれcProfileprofileで実行すると、次のエラーが発生します。

_pickle.PicklingError: Can't pickle <class '__main__.UpdateMessage'>: attribute lookup __main__.UpdateMessage failed

クラスを漬け込もうとしているようですが、なぜこれが起こっているのかわかりません。私のコードはこれを行わず、それがなくても問題なく動作するため、おそらくmultiprocessingモジュールです。しかし、なぜ pickle が必要なUpdateMessageのですか?どうすればエラーを修正できますか?

編集:これは、送信しているコードの一部ですUpdateMessage(スクリプトの複数の部分がこれを行いますが、すべて同じ方法です):

msg = UpdateMessage(uLref, refer[0] + marker[0] - 2,
                    slice(uL.shape[1]), ustar.copy())
queue.put(msg)

トレースバックはあまり役に立ちません:

Traceback (most recent call last):
  File "/usr/lib/python3.2/multiprocessing/queues.py", line 272, in _feed
    send(obj)
4

3 に答える 3

5

あなたのプロセスがどのように見えるかはわかりませんが、

'__main__.UpdateMessage'

起動したモジュールの UpdateMessage を参照します。

クラスの Module 以外で別のプロセスが起動された場合UpdateMessage、UpdateMessage は使用できません。

UpdateMessage so を含むそのモジュールをインポートする必要があります UpdateMessage.__module__ is not '__main__'

そうすれば、Pickle は他のプログラムでも UpdateMessage を見つけることができます。

次のようにすることをお勧め__main__.pyします。

import UpdateMessage_module

UpdateMessage_module.main()
于 2012-07-16T22:32:53.703 に答える
0

クラスが別のプロセスに送られる前に、クラスの酸洗いの試みが行われていると想定しています。最も簡単な解決策は、おそらく pickle-protocol をクラスに明示的に実装することです...

于 2012-07-16T21:43:05.787 に答える