【发布时间】:2017-02-02 21:01:46
【问题描述】:
这里我创建一个生产者-客户程序,父进程(生产者)创建多个子进程(消费者),然后父进程读取文件并将数据传递给子进程。
但是,这里出现了一个性能问题,在进程之间传递消息花费了太多时间(我认为)。
例如,200MB原始数据,父进程读取和预处理将花费不到8秒,而不是通过多进程将数据传递给子进程。pipe 将花费另外 8 秒,而子进程完成剩余工作只需花费另外 3 ~ 4 秒。
所以,一个完整的工作流程花费不到 18 秒,进程之间的通信花费超过 40% 的时间成本,比我想象的要大得多,我尝试了多进程。队列和经理,他们更糟糕。
我使用 windows7 / Python3.4。 我google了好几天,POSH可能是一个很好的解决方案,但它不能用python3.4构建
我有 3 种方法:
1.有没有什么办法可以直接在Python3.4中的进程之间共享python对象?作为POSH
或
2.是否可以将对象的“指针”传递给子进程,子进程可以恢复指向python对象的“指针”?
或
3.multiprocess.Array 可能是一个有效的解决方案,但如果我想共享复杂的数据结构,例如列表,它是如何工作的?我应该基于它创建一个新类并提供接口作为列表吗?
编辑1:
我尝试了第三种方法,但效果更差。
我定义了这些值:
p_pos = multiprocessing.Value('i') #producer write position
c_pos = multiprocessing.Value('i') #customer read position
databuff = multiprocess.Array('c',buff_len) # shared buffer
还有两个功能:
send_data(msg)
get_data()
在send_data函数(父进程)中,将msg复制到databuff,并通过管道将开始和结束位置(两个整数)发送给子进程。
与 get_data 函数(子进程)相比,它接收到两个位置并从 databuff 复制 msg。
最终,它的成本是使用管道@_@的两倍
编辑 2:
是的,我试过 Cython,结果看起来不错。
我只是将我的python脚本的后缀更改为.pyx并编译它,程序速度提高了15%。
毫无疑问,我遇到了“无法找到 vcvarsall.bat”和“系统找不到指定的文件”错误,我花了一整天的时间解决了第一个问题,并被第二个阻止了。
终于,我找到了Cyther,所有的烦恼都过去了^_^。
【问题讨论】:
-
我想要的只是一个队列,父进程将消息放入,子进程从中取出消息,并且在多进程模块中没有过多的移动操作,例如管道或队列
标签: multithreading performance python-3.x communication