Python对具有多个输入的函数进行多处理

Python对具有多个输入的函数进行多处理,python,multiprocessing,Python,Multiprocessing,在Python中,多处理模块可用于在一系列值上并行运行函数。例如,这将生成一个f的前100000次评估的列表 def f(i): return i * i def main(): import multiprocessing pool = multiprocessing.Pool(2) ans = pool.map(f, range(100000)) return ans 当f接受多个输入,但只有一个变量是变化的时,可以做类似的事情吗?例如,您将如何

在Python中,
多处理
模块可用于在一系列值上并行运行函数。例如,这将生成一个f的前100000次评估的列表

def f(i):
    return i * i

def main():
    import multiprocessing
    pool = multiprocessing.Pool(2)
    ans = pool.map(f, range(100000))

    return ans
当f接受多个输入,但只有一个变量是变化的时,可以做类似的事情吗?例如,您将如何将其并行化:

def f(i, n):
    return i * i + 2*n

def main():
    ans = []
    for i in range(100000):
        ans.append(f(i, 20))

    return ans

你可以用穷人的咖喱(又名包装):


然后致电
new\u f(i)

您可以使用穷人的咖喱(也称为包装):


然后调用
new\u f(i)

有几种方法可以做到这一点。在问题中给出的示例中,您可以只定义一个包装器函数

def g(i):
    return f(i, 20)
并将此包装传递给
map()
。一种更通用的方法是使用一个包装器,它接受一个元组参数,并将元组解压为多个参数

def g(tup):
    return f(*tup)

或者使用等效的lambda表达式:
lambda tup:f(*tup)

有几种方法可以实现这一点。在问题中给出的示例中,您可以只定义一个包装器函数

def g(i):
    return f(i, 20)
并将此包装传递给
map()
。一种更通用的方法是使用一个包装器,它接受一个元组参数,并将元组解压为多个参数

def g(tup):
    return f(*tup)
或者使用等效的lambda表达式:
lambda tup:f(*tup)

您可以使用

你可以用


如果您使用我的
多处理
分支,称为
pathos
,您可以获得包含多个参数的池…还可以使用
lambda
函数。它的好处是,您不必改变编程结构以适应并行工作

>>> def f(i, n):
...   return i * i + 2*n
... 
>>> from itertools import repeat
>>> N = 10000
>>>
>>> from pathos.pools import ProcessPool as Pool
>>> pool = Pool()
>>>
>>> ans = pool.map(f, xrange(1000), repeat(20))
>>> ans[:10]
[40, 41, 44, 49, 56, 65, 76, 89, 104, 121]
>>>
>>> # this also works
>>> ans = pool.map(lambda x: f(x, 20), xrange(1000))
>>> ans[:10]
[40, 41, 44, 49, 56, 65, 76, 89, 104, 121]

如果您使用我的
多处理
分支,称为
pathos
,您可以获得包含多个参数的池…还可以使用
lambda
函数。它的好处是,您不必改变编程结构以适应并行工作

>>> def f(i, n):
...   return i * i + 2*n
... 
>>> from itertools import repeat
>>> N = 10000
>>>
>>> from pathos.pools import ProcessPool as Pool
>>> pool = Pool()
>>>
>>> ans = pool.map(f, xrange(1000), repeat(20))
>>> ans[:10]
[40, 41, 44, 49, 56, 65, 76, 89, 104, 121]
>>>
>>> # this also works
>>> ans = pool.map(lambda x: f(x, 20), xrange(1000))
>>> ans[:10]
[40, 41, 44, 49, 56, 65, 76, 89, 104, 121]

这种技巧称为咖喱:

另一种不使用
functools.partial的方法是在
pool.map中使用经典的
map
命令:

def f(args):
   x, fixed = args
   # FUNCTIONALITY HERE

pool = multiprocessing.Pool(multiprocessing.cpu_count() - 1)
pool.map(f, map(lambda x: (x, fixed), arguments))

这种技巧称为咖喱:

另一种不使用
functools.partial的方法是在
pool.map中使用经典的
map
命令:

def f(args):
   x, fixed = args
   # FUNCTIONALITY HERE

pool = multiprocessing.Pool(multiprocessing.cpu_count() - 1)
pool.map(f, map(lambda x: (x, fixed), arguments))

Thils不支持多处理的映射,因为它不支持不可“导入”(使用pickle工具)的函数Thils不支持多处理的映射,因为它不支持不可“导入”(使用pickle工具)的函数我知道这是允许的,但为什么,假设只有在模块顶层定义的函数可以被pickle?您能澄清一下关于使用partial的时刻吗?看起来它忽略了参数的键:如果我想在第二个参数上pool.map-
partial(f,I=20)
-我得到了错误:参数得到了多个值
I
@Mikhail\u Sam您要添加到分部的函数需要将第一个参数作为位置参数(如运行for循环时的“I”),其余的关键字参数应该在这之后。“i”的所有值都作为列表/范围添加,作为“pool.map”函数的第二个参数。在您的示例中,当'i'的值已经作为'pool'函数的第二个参数可用时,您在分部函数中提供了'i'的值,这导致了自解释错误/i知道这是允许的,但为什么,假设只有在模块顶层定义的函数可以被pickle?您能澄清一下关于使用partial的时刻吗?看起来它忽略了参数的键:如果我想在第二个参数上pool.map-
partial(f,I=20)
-我得到了错误:参数得到了多个值
I
@Mikhail\u Sam您要添加到分部的函数需要将第一个参数作为位置参数(如运行for循环时的“I”),其余的关键字参数应该在这之后。“i”的所有值都作为列表/范围添加,作为“pool.map”函数的第二个参数。在您的示例中,当'i'的值已经作为'pool'函数的第二个参数可用时,您在分部函数中提供了'i'的值,这导致了自解释的错误/