本文介绍了并行化组合蟒蛇的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!
问题描述
如何并行化下面的代码,属性列中的元素数量接近15,因此组合花费了更多的时间。
combs = set()
for L in range(0,len(attributes)+1):
combs.add(itertools.combinations(attributes,L))
有没有办法使用多进程将其并行化?
我尝试过此操作,但遇到此错误。-如果区块大小<;=0:
TypeError:不可排序的类型:range()<;=int()
import itertools
from multiprocessing import Pool
def comb(attributes):
res = itertools.combinations(attributes)
return res
def main():
p = Pool(4)
times = range(0,len(attributes)+1)
values = p.map(comb,attributes,times)
p.close()
p.join()
print(values)
if __name__ == '__main__':
attributes =('Age', 'Workclass', 'Fnlwgt', 'Education', 'Education-num', 'marital-status', 'Occupation', 'Relationship', 'Race', 'Sex', 'Capital-gain', 'Capital-loss', 'Hours-per-week', 'Native country', 'Probability', 'Id')
main()
既然要求它解释这个问题,那就给你...我正在试着在没有替换的情况下得到密码。基本上是n!。例如,如果我的属性变量中有A、B、C,我尝试获取(A)、(B)、(C)、(A,B)、(A,C)、(A,B,C)。由于属性中的元素数量不是静态的,它会根据输入数据集而变化,所以我不能对其进行硬编码。因此,我在这里使用len(属性),其中的属性将存储数据集中的属性。然后,要创建组合,通常会创建长度为L的所有组合。在我的示例中,如果我给出了长度(属性),那么我将只得到ABC,而不是其他组合。所以我创建了一个长度范围,并用它添加一个范围来处理第零个元素。
现在回到问题上来,我的数据集中可能有15个元素,因此长度(属性)将是15,即15!这种组合生成需要花费大量的时间,因为它必须做这个阶乘。因此,我正在考虑将其并行化,使每个处理器一次处理一个组合集生成,例如,一个处理器将生成长度为2的所有组合和另一个长度为3的组合,依此类推。但在池映射中,我无法正确传递多个参数。希望这能澄清问题,如果需要进一步解释,请让我知道。推荐答案
您的多处理代码存在几个问题,这意味着它不能像单进程版本那样工作。
首先,您没有正确调用p.map
。map
方法的参数是要调用的函数、参数(单个序列)和块大小,指定一次向Worker传递多少个值。您正在将range
对象作为chunksize
传递,这是导致错误的直接原因。
如果您尝试修复它,您会发现其他问题。例如,您正在将attributes
传递给map
,这样它将只将单个值传递给每个工作进程,而不是整个属性列表。并且您的comb
函数返回组合值的迭代器,而不是值本身(因此Worker或多或少会立即完成,但返回一些无法打印出来的内容)。
以下是我认为可以工作的代码:
import itertools
from multiprocessing import Pool
# attributes is always accessible as a global, so worker processes can directly access it
attributes = ('Age', 'Workclass', 'Fnlwgt', 'Education', 'Education-num',
'marital-status', 'Occupation', 'Relationship', 'Race', 'Sex',
'Capital-gain', 'Capital-loss', 'Hours-per-week', 'Native country',
'Probability', 'Id')
def comb(n): # the argument n is the number of items to select
res = list(itertools.combinations(attributes, n)) # create a list from the iterator
return res
def main():
p = Pool(4)
times = range(0, len(attributes)+1)
values = p.map(comb, times) # pass the range as the sequence of arguments!
p.close()
p.join()
print(values)
if __name__ == '__main__':
main()
如果属性列表很大,这段代码仍然需要一段时间才能完成,但这只是因为有太多的值要打印出来(具有n
值的集合的Powerset有2^n
子集)。我的集成开发环境告诉我,输出超过88000行(谢天谢地,它没有全部显示)。如果问题的多处理部分不像输出部分那样不是问题,那就不足为奇了!
这篇关于并行化组合蟒蛇的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持编程学习网!
本站部分内容来源互联网,如果有图片或者内容侵犯您的权益请联系我们删除!