
本文介绍使用pandas分块读取(chunksize)、列筛选(usecols)和数据类型压缩(dtype)三大技术,高效过滤并处理千万级csv数据,避免内存溢出,同时保持代码简洁与可维护性。
本文介绍使用pandas分块读取(chunksize)、列筛选(usecols)和数据类型压缩(dtype)三大技术,高效过滤并处理千万级csv数据,避免内存溢出,同时保持代码简洁与可维护性。
处理数百万行的CSV文件时,一次性加载全部数据到内存极易触发MemoryError。根本解决思路不是“等机器升级”,而是改变数据加载范式:从“全量加载→过滤→计算”转向“流式分块→逐块过滤→增量写入”。以下提供经过生产验证的高效方案。
从 CSV 数据集生成图数据库加载器和三元组映射。将表格 CSV 数据转换为图数据库可直接使用的节点、边和三元组。
✅ 核心优化策略
- 按块读取(chunksize):将大文件切分为小批次(如1000–10000行),逐批处理,内存占用恒定;
- 按需加载列(usecols):只读取后续逻辑真正用到的字段(如age, salary),跳过无关列;
- 精简数据类型(dtype):用int8替代int64(年龄)、float32替代float64(薪资),内存可减少50%–75%;
- 边处理边写入(避免累积):不拼接所有块到一个DataFrame,而是每处理一块即追加写入结果文件,彻底规避内存堆积。
? 完整可运行示例
import pandas as pd
# 配置关键参数(根据实际数据调整)
CHUNK_SIZE = 5000
COLUMNS_NEEDED = ['age', 'salary', 'department'] # 仅读取必要列
DTYPES = {'age': 'int8', 'salary': 'int32', 'department': 'category'}
# 创建结果文件(含表头)
output_file = 'processed_file.csv'
with open(output_file, 'w', newline='') as f:
f.write('') # 清空或新建文件
# 分块处理并流式写入
for i, chunk in enumerate(pd.read_csv(
'large_file.csv',
chunksize=CHUNK_SIZE,
usecols=COLUMNS_NEEDED,
dtype=DTYPES,
low_memory=False # 避免dtype推断警告
)):
# ✅ 每块独立过滤(条件必须在chunk内完成)
filtered_chunk = chunk[(chunk['age'] > 30) & (chunk['salary'] > 50000)].copy()
# ✅ 添加新列(避免SettingWithCopyWarning)
filtered_chunk['bonus'] = (filtered_chunk['salary'] * 0.1).astype('float32')
# ✅ 追加写入,header仅在第一块写入
filtered_chunk.to_csv(
output_file,
mode='a',
header=(i == 0),
index=False
)
print(f"✅ 已处理第 {i+1} 块,写入 {len(filtered_chunk)} 行")
print(f"? 处理完成!结果已保存至 {output_file}")⚠️ 关键注意事项
- pd.concat() 是性能陷阱:示例答案中使用pd.concat([filtered_df, temp], axis=1)存在严重错误——axis=1是横向拼接(列合并),且不断累积DataFrame会迅速耗尽内存。务必改用流式写入(mode='a');
- copy() 防链式赋值:对filtered_chunk显式调用.copy(),避免SettingWithCopyWarning及不可预期行为;
- low_memory=False:关闭分块类型推断,提升读取稳定性(尤其当各块数据类型不一致时);
- category类型慎用:若department取值有限(如
- 测试先行:先用chunksize=100和小样本验证逻辑正确性,再逐步放大至生产参数。
通过以上组合策略,即使处理10GB+ CSV文件,也能在8GB内存机器上稳定运行。记住:大数据处理的本质,是让内存使用量与文件大小解耦——而分块+流式写入正是实现这一目标的最直接路径。

















