【发布时间】:2017-12-08 20:14:02
【问题描述】:
我正在尝试学习如何在 python 中进行并行编程。我写了一个简单的 int square 函数,然后串行、多线程、多进程运行:
import time
import multiprocessing, threading
import random
def calc_square(numbers):
sq = 0
for n in numbers:
sq = n*n
def splita(list, n):
a = [[] for i in range(n)]
counter = 0
for i in range(0,len(list)):
a[counter].append(list[i])
if len(a[counter]) == len(list)/n:
counter = counter +1
continue
return a
if __name__ == "__main__":
random.seed(1)
arr = [random.randint(1, 11) for i in xrange(1000000)]
print "init completed"
start_time2 = time.time()
calc_square(arr)
end_time2 = time.time()
print "serial: " + str(end_time2 - start_time2)
newarr = splita(arr,8)
print 'split complete'
start_time = time.time()
for i in range(8):
t1 = threading.Thread(target=calc_square, args=(newarr[i],))
t1.start()
t1.join()
end_time = time.time()
print "mt: " + str(end_time - start_time)
start_time = time.time()
for i in range(8):
p1 = multiprocessing.Process(target=calc_square, args=(newarr[i],))
p1.start()
p1.join()
end_time = time.time()
print "mp: " + str(end_time - start_time)
输出:
init completed
serial: 0.0640001296997
split complete
mt: 0.0599999427795
mp: 2.97099995613
但是,如您所见,发生了一些奇怪的事情,mt 与 serial 花费的时间相同,而 mp 实际上花费的时间要长得多(几乎长 50 倍)。
我做错了什么?有人可以将我推向正确的方向来学习 Python 中的并行编程吗?
编辑 01
查看 cmets,我发现可能不返回任何内容的函数似乎毫无意义。我什至尝试这样做的原因是因为之前我尝试了以下添加功能:
def addi(numbers):
sq = 0
for n in numbers:
sq = sq + n
return sq
我尝试将每个部分的加法返回到序列号加法器,因此至少我可以看到与纯序列实现相比有一些性能改进。但是,我不知道如何存储和使用返回的值,这就是我试图找出比这更简单的东西的原因,它只是划分数组并在其上运行一个简单的函数。
谢谢!
【问题讨论】:
-
你创建线程,启动它,然后等待它完成它的工作。为什么这应该比在主线程中执行相同的工作更快?是的,创建线程并不是一个快速的操作。
-
你重复你的
multiprocessing计算8次。加上产生一个进程的开销。要么预先分配工作并传递给每个进程一个块,要么使用pool。由于 GIL,线程不会加速 CPU 密集型任务。 -
那么我应该如何并行运行线程呢?
-
我已经对此进行了试验,得到了相同的结果,即使在允许创建所有
Processes -
@roganjosh 我在数组的 8 个不同部分运行了相同的函数。如何使用池或为每个进程传递一个块?
标签: python multithreading parallel-processing multiprocessing python-multiprocessing