2.274秒程序就运行完了!这便是原来版本的4倍加速。运行时间缩短的原因正是我们这次用4个CPU代替了1个CPU。
但是如果您仔细看看,您会看到“用户(User)”时间大概是接近9秒,如果程序2秒就运行结束了,为什么客户时间会是9秒?这似乎…有哪里不对?
其实这是因为”用户”时间是所有CPU时间的总和。我们和上次一样,用9秒的总CPU。
注意:启用Python进程以及给子进程分配数据都会占用时间,因此您不一定能靠这个方法大幅提高速度。如果您处理的数据量很大,这里有一篇“设置chunksize参数的技巧”文章可能可以帮助您:https://docs.python.org/3/library/concurrent.futures.html#concurrent.futures.Executor.map。
这种方法总能帮我的程序提速吗?
当你有一列数据,并且每个数据都可以独立处理的时候,使用Process Pools是一个好方法。这有一些适合使用并行处理的例子:
从一系列单独的网页服务器日志里抓取数据。
从一堆XML,CSV和JSON文件中解析数据。
对大量图片数据做预处理,建立机器学习数据集。
但Process Pools不是万能的。使用Process Pool需要在独立的Python处理过程中将数据来回传递。如果你正在使用的数据不能在处理过程中有效的被传递,这种方法就行不通。你处理的数据必须是Python知道怎么搞定的类型(https://docs.python.org/3 /library/pickle.html#what-can-be-pickled-and-unpickled)。
同时,数据不会按照一个预想的顺序被处理。如果你需要前一步的处理结果来进行下一步骤,这种方法也行不通。
那GIL怎么办?
你可能听说过Python有一个全局解释器锁(Global Interpreter Lock,),缩写为GIL。这意味着即使你的程序是多层的,每一层也只有一个Python命令能被执行。GIL确保任何时候都只有一个Python线程执行。 GIL最大的问题就是Python的多线程程序并不能利用多核CPU的优势。
但Process Pools能解决这个问题!因为我们在运行单独的Python实例,每个实例都有自己的GIL。这样你就有了真正的并行处理的Python代码!
不要害怕并行处理!
有了concurrent.futures库,Python可以让你简简单单地修改脚本,却能立刻调用你电脑上所有CPU内核开足马力地运行。不要害怕尝试。一旦你会用了,它就像写一个for循环那样简单,但会让整个程序快很多。
原文链接:
https://medium.com/@ageitgey/quick-tip-speed-up-your-python-data-processing-scripts-with-process-pools-cf275350163a
编辑:黄继彦
文末彩蛋
▼
首先感谢你一直以来的关注与支持!为了给你带来更好的服务和体验,我们诚挚的邀请你参与我们的问卷调查,帮助我们共同建设更好的数据派!
我们将挑选出10份参考价值较高的调查问卷,为提交者送出数据派精心准备的礼物,并择时公布中奖名单。
此活动大家自愿参与,所有信息我们都将严格保密。你的意见和建议将对我们的工作开展有很大的帮助!
扫描下方
二维码,或点击文末“阅读原文”填写问卷~