我有一个 bajillion 配对列表,每对大小相等。我想通过从每个索引中选择一个随机元素来“合并”每个元素,但是我当前的实现非常慢 -即使在多处理时也是如此。(FWIW,我的代码确实需要可线程化)。
def rand_merge(l1, l2):
newl = []
for i in range(len(l1)):
q = random.choice([l1, l2])
newl.append(q[i])
return newl
非常基本,但是在 20k 大小约 5-25 的列表上运行它,需要很长时间 - 我认为它是 random.choice 搞砸了工作。但我也尝试过其他版本的 random,比如创建一个由 0 和 1 组成的字符串来引用,不行。
编辑:更清晰:这是一种遗传算法,旨在通过匹配语料库来写句子。有问题的列表是按单词分割的句子。GA 正在将获胜的健身“父母”“合并”到孩子中,每个孩子都是两个父句子的“基因”的合并。这意味着“列表”确实需要匹配,并且不能从更大的列表列表中提取(我不认为)。
这里有一些代码...
from multiprocessing import Pool as ThreadPool
import random
def offspring(parents):
child = []
p1 = parents[0].split(' ')
p2 = parents[1].split(' ')
for i in range(min(len(p1), len(p2))):
q = random.choice([p1, p2])
child.append(q[i])
child = ' '.join([g for g in child]).strip()
return child
def nextgen(l): #l is two lists of previous generation and grammar seed
oldgen = l[0][:pop] # Population's worth of previous generation
gramsent = l[1] # this is the grammar seed
newgen = []
newgen.append(tuple([oldgen[0][0], oldgen[0][0]])) # Keep the winner!
for i in range(len(oldgen) - len(oldgen)//4):
ind1 = oldgen[0][0] # paired off against the winner - for larger pools, this is a random.sample/"tournament"
ind2 = oldgen[i][0]
newgen.append(tuple([ind1, ind2]))
pool = ThreadPool(processes=8)
newgen = pool.map(offspring, newgen)
pool.close()
pool.join()
人口和世代可以一起进入高数,并且每个句子都贯穿始终。自从最初发布问题以来,担心每一代人都需要很长时间才能滚动,我发现(对我来说令人头疼)漫长的处理时间实际上(几乎)与“人口”大小或数量无关的列表。每一代变异大约需要 15 秒。我将人口从 50 增加到 50000,代数从 15 秒增加到 17 秒左右。因此,缓慢显然隐藏在其他地方。
相关分类