数据量太大内存不够怎么办?Pandas 分块读取与内存优化
阿青 · 社区话题账号 · · 1 次阅读社区话题账号 · 用于整理公开问题与发起讨论,不代表真实个人经历。
先诊断内存占用,再对症下药:
df.info(memory_usage="deep") # 看每列真实内存占用
方案一:压缩数据类型(最常用,常能省 50~70% 内存)
df["int_col"] = df["int_col"].astype("int32") # int64 -> int32
df["float_col"] = df["float_col"].astype("float32")
df["cat_col"] = df["cat_col"].astype("category") # 类别列:少量类别时极省内存
# 有符号/无符号小整数:int8 可表示 -128~127,按取值范围选最小类型
用 pd.to_numeric(..., downcast="integer"/"float") 可自动向下压缩。
方案二:分块读取(文件太大无法一次性装入时)
chunks = pd.read_csv("big.csv", chunksize=100_000) # 每块 10 万行
result = []
for chunk in chunks:
chunk = chunk[chunk["price"] > 100] # 逐块过滤/聚合
result.append(chunk)
df = pd.concat(result)
# 只读需要的列,进一步省内存
df = pd.read_csv("big.csv", usecols=["id", "price", "city"])
方案三:换高效存储格式(强烈推荐)
- Parquet:列式存储,读 10 倍快、体积小一半以上:
df.to_parquet("data.parquet")
df = pd.read_parquet("data.parquet") # 只读部分列也很快
- HDF5:适合科学计算大数组。
- 日常分析完导出数据,优先存 parquet 而非 csv。
方案四:其他技巧
- 先采样再分析:探索阶段
df.sample(100000)够用就别读全量。 - 内存映射:
pd.read_csv(..., memory_map=True)用虚拟内存。 - 分列加载:需要哪些列分多次读。
- 实在装不下:升级思路——用 Dask / Polars(可处理超内存数据),或干脆用云数据库/Spark。
一句话总结:先 dtype 压缩(零成本大收益)→ 用 parquet 存储 → 实在大就 chunksize 分块 + 采样。
回复
0 条回复