所以我制作了一个程序来计算素数,以测试使用多线程和仅使用单线程之间的区别。我读到多处理绕过了GIL,所以我预计性能会有不错的提升。
所以这里我们有我的代码来测试它:
def prime(n):
if n == 2:
return n
if n & 1 == 0:
return None
d= 3
while d * d <= n:
if n % d == 0:
return None
d= d + 2
return n
loop = range(2,1000000)
chunks = range(1,1000000,1000)
def chunker(chunk):
ret = []
r2 = chunk + 1000
r1 = chunk
for k in range(r1,r2):
ret.append(prime(k))
return ret
from multiprocessing import cpu_count
from multiprocessing.dummy import Pool
from time import time as t
pool = Pool(12)
start = t()
results = pool.map(prime, loop)
print(t() - start)
pool.close()
filtered = filter(lambda score: score != None, results)
new = []
start = t()
for i in loop:
new.append(prime(i))
print(t()-start)
pool = Pool(12)
start = t()
results = pool.map_async(chunker, chunks).get()
print(t() - start)
pool.close()
我执行的程序和这个地方的时间:
multi processing without chunks:
4.953783750534058
single thread:
5.067057371139526
multiprocessing with chunks:
5.041667222976685
也许你已经注意到了,但多处理并没有那么快。我有一个6核12线程AMD ryzen CPU,所以我认为如果我能使用所有这些线程,我的性能至少会翻倍。但没有。如果我在任务管理器中查看,使用多处理的平均cpu使用率为12%,而单线程使用率约为10%。
那到底发生了什么?我做错什么了吗?或者,能够绕过GIL并不意味着能够使用更多的核心?如果我不能在多处理中使用更多的核心,那么我该怎么做呢?
from multiprocessing.dummy import Pool
from time import time as t
pool = Pool(12)
来自文件:
multiprocessing.dummy
复制multiprocessing
的API,但只不过是threading
模块的包装器。
换句话说,您仍然在使用线程,而不是进程。
要使用进程,请执行from multiprocessing import Pool
。