You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Python大文件多进程处理:如何规避内存超限问题?

处理大文件的Python多进程优化方案

问题描述

我有一个几GB到几十GB的大数据文件,希望用Python通过多进程进行读取和处理。当前做法是将文件分块(比如100MB),并将这些块传递给进程,代码如下:

from multiprocessing import Pool

with Pool(processes=8) as pool:
    file_chunk = readFileInJunks() #iterator
    for i in range(8):
        pool.apply_async(f, (next(file_chunk),))
    pool.close()
    pool.join()

但当文件大小超过内存时,这种方法会触发内存限制。我的疑问是:如何避免触发内存限制?

我可以让每个进程自行加载数据块,但这会导致n个进程同时访问同一文件,可能会降低读取速度(尤其是老旧磁盘)。另一种选择是在进程池有空位时手动调用apply_async,但这在某种程度上失去了进程池的意义。有没有更优雅的处理方式?


解决方案:用Pool.imap/imap_unordered配合生成器实现懒加载

核心思路

利用生成器逐块读取文件(避免一次性加载整个文件到内存),结合进程池的imap或imap_unordered方法,让进程池自动从生成器中获取空闲进程所需的数据块,无需手动管理任务提交,同时保证只有主进程负责文件读取,避免多进程磁盘IO竞争。

代码示例

1. 二进制文件处理

from multiprocessing import Pool

def process_chunk(chunk):
    # 替换为你的实际数据处理逻辑
    # 比如解析二进制数据、计算统计值等
    return len(chunk)

def read_binary_chunks(file_path, chunk_size=100*1024*1024):
    """生成器:逐块读取二进制文件,避免内存溢出"""
    with open(file_path, 'rb') as f:
        while chunk := f.read(chunk_size):
            yield chunk

if __name__ == '__main__':
    # 初始化8进程池
    with Pool(processes=8) as pool:
        # imap会自动将生成器的块分配给空闲进程,懒加载不占内存
        for result in pool.imap(process_chunk, read_binary_chunks('large_data.bin')):
            # 可选:处理每个块的结果,不需要可忽略
            print(f"处理完成一个块,结果:{result}")

2. 文本文件处理(保证行完整)

如果是文本文件,需要避免将一行拆分为两个块,可调整生成器逻辑:

def read_text_chunks(file_path, chunk_size=100*1024*1024):
    """生成器:按块读取文本文件,保证每个块包含完整的行"""
    with open(file_path, 'r', encoding='utf-8') as f:
        buffer = ''
        while True:
            chunk = f.read(chunk_size)
            if not chunk:
                if buffer:
                    yield buffer
                break
            # 找到最后一个换行符,拆分块与缓冲区
            last_newline = chunk.rfind('\n')
            if last_newline == -1:
                buffer += chunk
            else:
                yield buffer + chunk[:last_newline+1]
                buffer = chunk[last_newline+1:]

# 后续处理逻辑同二进制文件,替换read_binary_chunks为read_text_chunks即可

优势说明

  • 内存友好:生成器每次仅读取一个块到内存,不会加载整个文件,彻底避免内存溢出。
  • 进程池自动调度:imap/imap_unordered会自动将数据块分配给空闲进程,无需手动调用apply_async,完全发挥进程池的管理优势。
  • 磁盘IO优化:只有主进程负责文件读取,子进程仅处理数据,避免多进程同时读文件的IO竞争,尤其适合老旧机械硬盘。
  • 可选顺序控制:需要保持处理结果与文件顺序一致时用imap,不需要顺序时用imap_unordered,后者效率更高。

内容的提问来源于stack exchange,提问作者Regedit

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.18 11:47:28