fillna() 卡死主因是默认按列填充时的索引对齐与混合类型反复推断,导致内存和cpu双爆;应先查dtype、强转数值列、按列处理、禁用自动类型提升。

为什么 fillna() 直接用在千万行上会卡死?
因为默认的 fillna() 在 axis=0(按列)时,内部会尝试做完整索引对齐和类型推断,尤其当列含混合类型(比如 object 列里混着 None、空字符串、数字字符串)时,Pandas 会逐元素调用 isna() 并反复 infer 类型,内存和 CPU 双爆。你看到进程不动,大概率是卡在类型推断或链式拷贝上。
实操建议:
- 先用
df.dtypes检查每列真实 dtype,把明显该是数值但被识别成object的列用pd.to_numeric(..., errors='coerce')强转 - 避免对整张表调用
df.fillna(value)—— 改为按列处理,且只处理明确需要填充的列 - 禁用自动类型提升:传入
downcast=False(默认是'infer'),防止 Pandas 尝试压缩 int64 → int32
数值列用 fillna(method='ffill') 时为何结果不对?
因为 method='ffill' 默认按 axis=0(即纵向向下填充),但如果你的数据是按时间分块读取、再拼接的,索引不连续或有重复,ffill 会跨块“泄露”前一块末尾值到后一块开头,造成逻辑错误。这不是 bug,是设计如此 —— 它只认索引顺序,不管业务语义。
实操建议:
- 确认是否真需要前向填充:多数千万级场景(如传感器日志、订单流水)更应按业务分组填充,比如
df.groupby('device_id')['temp'].ffill() - 若必须全局 ffill,先重置索引:
df = df.reset_index(drop=True),否则稀疏索引会让填充跳过大量行 -
limit参数慎用:设limit=1看似安全,但在并行 chunk 处理中可能让相邻 chunk 边界处漏填
如何用 chunksize + dtype 预设规避 OOM?
读 CSV 时不用 pandas.read_csv() 一次性加载,而是用 chunksize 流式处理;但如果不提前指定 dtype,每个 chunk 仍会独立推断类型,导致后续 concat 时列类型不一致(比如一个 chunk 的 price 是 float64,另一个是 object),引发隐式转换和内存翻倍。
SkillSub Pro - Python 题解与代码注释双功能技能功能概述SkillSub Pro - Python 题解与代码注释双功能技能是一项面向实际任务的技能,主要用于SkillSub Pro 是一个 Python 题解生成与代码注释的 双功能合体技能 ,专为学生、算法学习者和开发者设计;✅ 一个技能,两种用途 :;核心要点📝 题解模式 :输入题目/题号,自动生成完整 Python 题解(含详细注释、解题思路、复杂度分析);💬 注释模式 :输入 Python 代码,自动添加详细中。它将相关步骤、
实操建议:
- 先用小样本跑一次
pd.read_csv('sample.csv', nrows=10000).dtypes,保存为字典dtypes_dict - 读取时显式传入:
pd.read_csv(path, chunksize=50000, dtype=dtypes_dict, low_memory=False) - 每个 chunk 填充后立刻写入磁盘(如 parquet):
chunk_filled.to_parquet(f'filled_{i}.parq', index=False),别堆在内存里 concat
用 scikit-learn 的 SimpleImputer 真比 Pandas 快吗?
只在数值列多、缺失模式规则(比如固定列需均值填充)时快 —— 因为 SimpleImputer 底层用 NumPy 向量化计算,不走 Pandas 的 object 循环路径。但它强制要求输入是二维 array,会丢掉列名和索引,且无法处理 object 列的字符串填充(比如用众数填分类变量)。
实操建议:
- 数值列统一处理:提取
df.select_dtypes(include='number').values,用SimpleImputer(strategy='mean').fit_transform(),再塞回原 DataFrame 对应位置 - 分类列单独处理:用
df['category'].mode()[0]获取众数,再用fillna(),别强塞进SimpleImputer - 注意
SimpleImputer的missing_values默认是np.nan,如果数据里存的是'N/A'或-999,得手动替换或改参数
千万级数据的填充瓶颈往往不在算法本身,而在类型混乱、索引冗余、内存碎片 —— 先 fix dtype 和索引,比换库更立竿见影。
Python免费学习笔记(深入):立即使用
在学习笔记中,你将探索 Python 的核心概念和高级技巧!










