Этот вопрос относится к этим другим сообщениям на SO, однако предлагаемые там решения, похоже, не работают для моего случая. Вкратце, моя проблема может быть проиллюстрирована на следующем примере. У меня есть класс Algebra
, где с помощью метода triPower
я стремлюсь вычислить мощность тринома, то есть (a+b+c)**n
для многих n
значений с фиксированным a, b, c
. Для этого я подумал о создании метода _triPower(a,b,c,n)
и передаче его в мою pool.map()
функцию с помощью functools.partial(_triPower,...)
, где я фиксирую a, b, c
и оставляю n
в качестве единственного параметра, так как я работаю в Python 2.7 и map
из модуля multiprocessing
требуется только одна функция аргумента (см. В противном случае этот пост ). Код следующий:
from __future__ import division
import numpy as np
import functools as fntls
import multiprocessing as mp
import multiprocessing.pool as mppl
# A couple of classes introduced to allow multiple processes to have their own daemons (parallelization)
class NoDaemonProcess(mp.Process):
# make 'daemon' attribute always return False
def _get_daemon(self):
return False
def _set_daemon(self, value):
pass
daemon = property(_get_daemon, _set_daemon)
# We sub-class multiprocessing.pool.Pool instead of multiprocessing.Pool
# because the latter is only a wrapper function, not a proper class.
class MyPool(mppl.Pool):
Process = NoDaemonProcess
# Sample class where I want a method to run a parallel loop
class Algebra(object):
def __init__(self,offset):
self.offset = offset
def trinomial(self,a,b,c):
return a+b+c
def _triPower(self,a,b,c,n):
"""This is the method that I want to run in parallel from the next method"""
return self.offset + self.trinomial(a,b,c)**n
def triPower(self,n):
pls = MyPool(4)
vals = pls.map(fntls.partial(self._triPower,a=1.,b=0.,c=1.),n)
print vals
# Testing
if __name__ == "__main__":
A = Algebra(0.)
A.triPower(np.arange(0.,10.,0.01))
Выше не работает и выдает (как и ожидалось от этот пост ) ошибку:
cPickle.PicklingError: Can't pickle <type 'instancemethod'>: attribute lookup __builtin__.instancemethod failed
Следовательно, следуя тому же посту, я попытался определить _triPower
как глобальную функцию, т.е.
def _triPower(alg,a,b,c,n):
"""This is the method that I want to run in parallel from the next method"""
return alg.trinomial(a,b,c)**n
и затем редактирование Algebra.triPower(...)
в соответствии с:
def triPower(self,n):
pls = MyPool(4)
vals = pls.map(fntls.partial(_triPower, alg=self, a=1., b=0., c=1.), n)
print vals
и этот последний вместо этого выдает странную ошибку TypeError, такую как:
TypeError: _triPower() got multiple values for keyword argument 'alg'
С другой стороны, предложение попытаться сделать методы сериализуемыми с помощью VeryPicklableObject , как в , этот другой пост , кажется, также не работает, и этот пакет кажется мертвым (на момент 05/2019). Так что я делаю не так и как я могу заставить мои вычисления выполняться параллельно?