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

如何优化pandas DataFrame的explode操作,降低大文件处理内存占用?

大尺寸CSV多列分隔符拆分的低内存实现方案

原代码内存溢出的核心原因是一次性加载全量数据到内存,拆分+爆炸操作会使数据量成倍放大,叠加pandas的内存开销导致超出硬件限制。以下是三种可落地的优化方案,内存占用均可控制在1G以内:

方案1:pandas分块处理(无需换依赖,兼容原有逻辑)

利用pandas read_csv 的分块读取能力,每次只加载少量数据处理后写入结果,全程不会加载全量数据到内存:

import pandas as pd

# 配置项
INPUT_CSV = "your_source.csv"
OUTPUT_CSV = "processed_result.csv"
SPLIT_COLS = ["id"]  # 支持配置多列同时拆分,比如["id", "tag"]
SEPARATOR = "|"
CHUNKSIZE = 100000  # 可根据内存调整,内存不足可降到50000

first_chunk = True
# 分块读取,同时提前指定列数据类型降低内存占用
for chunk in pd.read_csv(
    INPUT_CSV,
    chunksize=CHUNKSIZE,
    dtype={
        "uid": "int32",
        "tag": "category",
        "date": "category"
    }
):
    # 拆分所有需要处理的列
    for col in SPLIT_COLS:
        chunk[col] = chunk[col].str.split(SEPARATOR)
    # 同时爆炸所有拆分列,避免多次操作产生冗余数据
    chunk = chunk.explode(SPLIT_COLS)
    # 去重,可指定subset参数按主键去重,比全列判断更省资源
    chunk = chunk.drop_duplicates(subset=["id", "uid", "date"])
    # 追加写入结果文件
    chunk.to_csv(OUTPUT_CSV, mode="a", header=first_chunk, index=False)
    first_chunk = False

方案2:逐行流式处理(内存占用最低,<100M)

用Python内置csv模块逐行处理,完全不需要加载全表到内存,适合极端内存受限场景:

import csv
from itertools import product

# 配置项
INPUT_CSV = "your_source.csv"
OUTPUT_CSV = "processed_result.csv"
SPLIT_COLS = ["id"]
SEPARATOR = "|"
FILE_DELIMITER = "\t"  # 你的CSV如果是逗号分隔就改成","
NEED_DEDUPLICATE = True

seen = set()
with open(INPUT_CSV, "r", encoding="utf-8") as f_in, \
     open(OUTPUT_CSV, "w", encoding="utf-8", newline="") as f_out:
    reader = csv.DictReader(f_in, delimiter=FILE_DELIMITER)
    writer = csv.DictWriter(f_out, fieldnames=reader.fieldnames)
    writer.writeheader()

    for row in reader:
        # 拆分所有指定列
        split_values = [row[col].split(SEPARATOR) for col in SPLIT_COLS]
        # 生成多列拆分后的所有组合
        for vals in product(*split_values):
            new_row = row.copy()
            for idx, col in enumerate(SPLIT_COLS):
                new_row[col] = vals[idx]
            # 去重逻辑,不需要可以直接删除
            if NEED_DEDUPLICATE:
                row_key = tuple(new_row.values())
                if row_key in seen:
                    continue
                seen.add(row_key)
            writer.writerow(new_row)

方案3:Polars处理(性能最高,速度是pandas的5~10倍)

Polars是Rust实现的高性能数据处理库,默认采用内存映射+懒执行,处理1G级文件完全不需要加载全量数据到内存,代码更简洁:
首先安装依赖:pip install polars

import polars as pl

# 配置项
INPUT_CSV = "your_source.csv"
OUTPUT_CSV = "processed_result.csv"
SPLIT_COLS = ["id"]
SEPARATOR = "|"
FILE_DELIMITER = "\t"

# 懒加载CSV,不占用内存
df = pl.scan_csv(INPUT_CSV, separator=FILE_DELIMITER)
# 拆分+爆炸多列
for col in SPLIT_COLS:
    df = df.with_columns(pl.col(col).str.split(SEPARATOR)).explode(col)
# 去重,可指定subset参数按主键去重
df = df.unique(subset=["id", "uid", "date"])
# 执行计算并写入结果
df.write_csv(OUTPUT_CSV)

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.01 20:54:05