简体   繁体   English

为什么 ThreadPoolExecutor 比 for 循环慢?

[英]Why is ThreadPoolExecutor slower than for loop?

Code 1代码 1

def feedforward(self,d):
    out = []
    for neuron in self.layer:
        out.append(neuron.feedforward(d))
    return np.array(out)

This the original code I've written for performing a feedforward.这是我为执行前馈而编写的原始代码。 I wanted to improve the speed of execution using multithreading so i edited the code to use ThreadPoolExecutor from concurrent.futures module我想使用多线程提高执行速度,所以我编辑了代码以使用concurrent.futures模块中的ThreadPoolExecutor

Code 2代码 2

def parallel_feedforward(self,func,param):
    return func.feedforward(param)

def feedforward(self,d):
    out = []
    with ThreadPoolExecutor(max_workers = 4) as executor:
        new_d = np.tile(d,(len(self.layer),1))
        for o in executor.map(self.parallel_feedforward,self.layer,new_d):
            out.append(o)
    return np.array(out)

variable d is a vector, i used np.tile() so that the executor.map takes the input properly变量d是一个向量,我使用np.tile()以便executor.map正确接受输入

After timing the the speed of execution of both.计时后两者的执行速度。 I found out that the Code 1 is significantly faster than the Code 2 (Code 2 is almost 8-10 times slower).我发现代码 1 比代码 2 快得多(代码 2 几乎慢了 8-10 倍)。 But wouldn't the code using multithreading be faster than it's loop counterpart.但是使用多线程的代码不会比循环对应的代码更快。 Is it because the code I've written is wrong or is it because of something else.是因为我写的代码是错误的,还是因为其他原因。 If it is because of some mistake in my code, can someone tell me what have i did wrong?.如果是因为我的代码中的一些错误,有人可以告诉我我做错了什么吗?

Thanks for your help in advance.提前感谢您的帮助。

Hari,哈里,

you should do a quick google on python and threads - notably that python "threads" won't run in parallel because of the python GIL (...google it).你应该在 python 和线程上做一个快速的谷歌搜索 - 特别是 python “线程”不会因为 python GIL 并行运行(......谷歌它)。 So if you function above is CPU-bound, then it won't actually run faster using python threads as you've got above.因此,如果您上面的 function 受 CPU 限制,那么使用上面的 python 线程实际上不会运行得更快。

To really run in parallel, you need to be using ProcessPoolExecutor instead - that gets around the python "GIL lock" that is present with threading.要真正并行运行,您需要改用 ProcessPoolExecutor - 它绕过了线程存在的 python“GIL 锁”。


As to why it might run 8-10 times slower - just one thought is that when you use futures, when you make a call with arguments to an executor, futures will pickle up your arguments to pass to the workers, who will then un-pickle in the thread/process to use there.至于为什么它的运行速度可能会8-10 倍 - 只是一个想法是,当您使用期货时,当您使用 arguments 向执行者调用时,期货会提取您的 arguments 以传递给工人,然后工人将取消- pickle 在线程/进程中使用。 (if this is new to you, do a quick google on python pickling) (如果这对你来说是新的,在 python 酸洗上做一个快速的谷歌)

If you have arguments that are non-trivial in size, this can take a large amount of time.如果您有尺寸不小的 arguments,这可能需要大量时间。

So this could be why you're seeing the slowdown.所以这可能就是你看到放缓的原因。 ...I have seen a huge slowdown in my own code because I tried to pass large sized arguments to workers. ...我看到我自己的代码出现了巨大的减速,因为我试图将大尺寸的 arguments 传递给工人。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM