Python多处理内存使用
我写了一个程序,可以总结如下:Python多处理内存使用,python,linux,memory-management,multiprocessing,Python,Linux,Memory Management,Multiprocessing,我写了一个程序,可以总结如下: def loadHugeData(): #load it return data def processHugeData(data, res_queue): for item in data: #process it res_queue.put(result) res_queue.put("END") def writeOutput(outFile, res_queue):
def loadHugeData():
#load it
return data
def processHugeData(data, res_queue):
for item in data:
#process it
res_queue.put(result)
res_queue.put("END")
def writeOutput(outFile, res_queue):
with open(outFile, 'w') as f
res=res_queue.get()
while res!='END':
f.write(res)
res=res_queue.get()
res_queue = multiprocessing.Queue()
if __name__ == '__main__':
data=loadHugeData()
p = multiprocessing.Process(target=writeOutput, args=(outFile, res_queue))
p.start()
processHugeData(data, res_queue)
p.join()
真正的代码(尤其是writeOutput()
)要复杂得多writeOutput()
仅使用这些作为参数的值(这意味着它不引用数据
)
基本上,它将一个巨大的数据集加载到内存中并进行处理。输出的写入被委托给一个子进程(它实际上写入多个文件,这需要很多时间)。
因此,每次处理一个数据项时,它都会通过res_队列发送到子进程,而子进程又会根据需要将结果写入文件中
子进程不需要以任何方式访问、读取或修改loadHugeData()
加载的数据。子进程只需要使用主进程通过res\u queue
发送给它的内容。这就引出了我的问题
在我看来,子进程获得了巨大数据集的自身副本(使用top
检查内存使用情况时)。这是真的吗?如果是这样的话,我如何避免id(基本上使用双内存)
我使用的是Python 2.6,程序在linux上运行。多处理模块有效地基于创建当前进程副本的
fork
系统调用。由于您在fork
(或创建多处理.Process
)之前加载了大量数据,因此子进程将继承数据的一个副本
但是,如果您正在运行的操作系统实现了COW(写时复制),则物理内存中实际上只有一个数据副本,除非您在父进程或子进程中修改数据(父进程和子进程将共享相同的物理内存页,尽管在不同的虚拟地址空间中);即使这样,也只会为更改分配额外内存(以pagesize
增量)
您可以通过在加载大量数据之前调用
多处理.Process
来避免这种情况。那么,当您将数据加载到父进程中时,额外的内存分配将不会反映在子进程中。比我快,做得好。Linux是COW,因此当父进程写入数据时,数据将被复制。如果父进程只读取数据,那么将只有一个数据实例,但top(我几乎可以肯定)将显示属于这两个进程的数据。meminfo应该提供更准确的内存使用数据。我认为现在最常见的操作系统是COW(我只是想尽量做到通用)。很好的特性,但在解释基于进程的内存报告工具(即top、ps等)的输出时,常常会引起混淆pmap
也将正确报告;但是不知道Windows:)还要注意,每个Python对象都包含一个引用计数,每当访问该对象时,该计数都会被修改。因此,仅仅读取一个数据结构就可能导致COW复制.Ty作为答案。在加载数据之前调用multiprocessing.Process
,似乎解决了这个问题。我还将研究meminfo
。@isedev甚至对表达式求值都会涉及临时引用。您能否重新构造代码以使用迭代器,而不是加载所有loadHugeData?如果它看起来是load/process/enqueue/dequeue/write,那么您可能会这样做。不幸的是,“hugeData”是一个以制表符分隔的txt文件,基本上包含一个稀疏数组。我需要在处理过程中根据行号“随机访问”这些数据。因此,将其加载到内存中(使用稀疏阵列特定优化)会使处理速度大大加快。建议使用类似“的方式进行流程集成”可能会大大超过工程设计,但了解它是否有帮助/可扩展/性能会很有趣。和往常一样,别人的问题总是更有趣。