python-3.x - Python 多处理使 OSX 刹车
问题描述
我有一个程序,它从一副牌中随机选择 13 张牌,并分析牌的形状、点数和其他一些对桥牌游戏很重要的特征。该程序将在大约 5 分钟内选择和分析 10**7 手牌。检查活动监视器显示,在执行期间,CPU(即 6 核处理器)将大约 9% 的时间用于程序,而大约 90% 的时间处于空闲状态。所以它看起来像是多处理的主要候选者,我使用队列创建了一个多处理版本,将信息从每个进程传递回主程序。解决了 IDLE 无法工作的问题后,将进行多处理(我现在使用 PyCharm 运行它),并且在进程完成冻结程序之前对其进行连接,我让它开始工作。
但是,无论我使用多少个进程 5、10、25 或 50,结果总是相同的。CPU 将大约 18% 的时间用于程序,大约 75% 的时间处于空闲状态,执行时间在 10 分钟多一点时增加了一倍多。
谁能解释我如何让进程占用更多的 CPU 时间以及如何让执行时间来反映这一点?以下是该计划的相关部分:
import random
import collections
import datetime
import time
from math import log10
from multiprocessing import Process, Queue
NUM_OF_HANDS = 10**6
NUM_OF_PROCESSES = 25
def analyse_hands(numofhands, q):
#code remove as not relevant to the problem
q.put((distribution, points, notrumps))
if __name__ == '__main__':
processlist = []
q = Queue()
handsperprocess = NUM_OF_HANDS // NUM_OF_PROCESSES
print(handsperprocess)
# Set up the processes and get them to do their stuff
start_time = time.time()
for _ in range(NUM_OF_PROCESSES):
p = Process(target=analyse_hands, args=((handsperprocess, q)))
processlist.append(p)
p.start()
# Allow q to get a few items
time.sleep(.05)
while not q.empty():
while not q.empty():
#code remove as not relevant to the problem
# Allow q to be refreshed so allowing all processes to finish before
# doing a join. It seems that doing a join before a process is
# finished will cause the program to lock
time.sleep(.05)
counter['empty'] += 1
for p in processlist:
p.join()
while not q.empty():
# This is never executed as all the processes have finished and q
# emptied before the join command above.
#code remove as not relevant to the problem
finish_time = time.time()
解决方案
对于 IDLE 无法正确运行多处理器启动指令的原因,我没有答案,但我相信执行时间加倍的答案在于我正在处理的问题类型。也许其他人可以发表评论,但在我看来,在队列中添加和删除项目所涉及的开销非常高,因此当通过队列传递的数据量与数量相比较小时,性能改进将得到最好的实现获得该数据所需的处理。
在我的程序中,我正在创建和传递 10**7 项数据,我想这是通过队列传递这些项目的开销,这会扼杀通过单独进程获取数据的任何性能改进。通过使用地图,似乎所有 10^7 项数据都需要存储在地图中,然后才能进行任何进一步的处理。这可能会提高性能,具体取决于使用地图和处理大量数据的开销,但目前我将坚持使用我原来的原始单处理代码。
推荐阅读
- pywinauto - 如何在 VM 窗口中键入键?
- flutter - 想用 Flutter 开发小程序
- python - 用python求解具有负幂或非整数幂的多项式方程
- xml - 检查元素是否存在,如果不添加特定元素
- continuous-integration - TeamCity - 获取构建服务器日志 | 当前构建
- c# - 创建可供VB使用的C# WPF DLL
- swift - 使用 performSegue 视图时停止 webview 重新加载
- linux - 通过 SSH 和 FTP 安装包管理器
- c# - ASP.NET Core 2.1 中的远程验证值未传递给控制器
- ruby-on-rails - ActiveRecord 不再在数组中查找重复的 ID 并保存为拥有和属于多的关系,Rails 4.2.8