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

如何在Pandas中按列名填充默认值并避免TypeError错误

解决按列名规则填充缺失值的类型错误问题

首先,咱们来拆解你遇到的问题:你用np.select的写法存在逻辑偏差,再加上之前将列转为Int64(可空整数类型)的操作,共同导致了类型不兼容的错误。下面一步步帮你梳理解决:

错误原因分析

  1. np.select用法错误:它需要的是元素级的填充值,但你传入的是整个DataFrame调用fillna后的结果,这会导致维度和数据类型的冲突,无法正确匹配每一列的规则。
  2. Int64类型兼容性问题:Int64(大写I)是Pandas的可空整数类型,当你直接填充普通的0(int类型)时,会因为类型不匹配抛出转换错误。

正确的解决方案

我们可以分类型对列进行针对性处理,逻辑更清晰,也能避免类型冲突:

步骤1:先处理日期/时间列

首先把所有包含date的列转为Pandas datetime类型,再用指定日期填充缺失值:

import pandas as pd
import numpy as np

# 你的原始DataFrame
obs = pd.DataFrame({
    'person_id' :[1,2,3],
    'obs_date':['12/31/2007','11/25/2009',np.nan], 
    'hero_id':[2,4,np.nan],
    'date':['12/31/2017',np.nan,'10/06/2015'], 
    'heroine_id':[1,np.nan,5],
    'datetime':['12/31/2027','11/25/2029',np.nan], 
    'bud_source_value':[1250000,250000,np.nan], 
    'prod__source_value':[10000,20000,np.nan]
})

# 筛选所有含'date'的列,转为datetime类型
date_cols = obs.columns[obs.columns.str.contains('date')]
obs[date_cols] = obs[date_cols].apply(pd.to_datetime, errors='coerce')

# 用指定日期填充缺失值(转成datetime对象避免类型问题)
fill_date = pd.to_datetime('12/31/2000')
obs[date_cols] = obs[date_cols].fillna(fill_date)

步骤2:处理以'id'结尾的列

对于这类列,我们填充0,同时兼容Int64类型(如果需要保留可空整数特性):

id_cols = obs.columns[obs.columns.str.endswith('id')]
# 先填充0,再转为Int64类型(避免直接填充int导致的类型冲突)
obs[id_cols] = obs[id_cols].fillna(0).astype('Int64')
# 如果不需要可空整数,直接转普通int即可:obs[id_cols] = obs[id_cols].fillna(0).astype(int)

步骤3:以'value'结尾的列

这类列无需任何操作,保持原有的np.nan即可。

替代方案:用字典批量填充

如果你喜欢更简洁的写法,可以用fillna的字典参数,一次性指定各列的填充规则:

# 构建填充规则字典
fill_rules = {}
# id列填充0
for col in obs.columns[obs.columns.str.endswith('id')]:
    fill_rules[col] = 0
# 日期列填充指定日期
fill_date = pd.to_datetime('12/31/2000')
for col in obs.columns[obs.columns.str.contains('date')]:
    fill_rules[col] = fill_date

# 先转换日期列类型,再批量填充
obs[date_cols] = obs[date_cols].apply(pd.to_datetime, errors='coerce')
obs = obs.fillna(fill_rules)

# 最后处理id列的Int64类型(如果需要)
obs[id_cols] = obs[id_cols].astype('Int64')

关于你之前的astype('float').astype('Int64')代码

这段代码本身是将列转为可空整数类型的常用方法(因为直接转Int64不允许存在NaN,所以先转float过渡),但如果之后填充0时用普通int类型,就会和Int64类型冲突。所以正确的顺序应该是先填充0,再转为Int64类型,这样就能避免类型转换错误。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.04.30 16:02:44