使用Sklearn独热编码后合并DataFrame出现NaN值的原因及优化方案求助
问题描述
我正在使用Scikit-learn库处理薪资预测数据集,已通过dropna()清理含NaN值的行,确认特征集X(包含Age、Years of Experience列)无空值;使用ColumnTransformer和OneHotEncoder对Gender、Education Level列编码生成df_ohe,且df_ohe也无空值,但将X与df_ohe通过join合并后,独热编码列出现了NaN值。
相关代码:
from sklearn.preprocessing import OneHotEncoder from sklearn.compose import ColumnTransformer import pandas as pd myTransformer = ColumnTransformer( transformers=[('one_hot_encoder', OneHotEncoder(), ['Gender', 'Education Level'])], ) transformed = myTransformer.fit_transform(X) columns = myTransformer.named_transformers_['one_hot_encoder'].get_feature_names_out(['Gender', 'Education Level']).tolist() df_ohe = pd.DataFrame(transformed, columns=columns) display(df_ohe) print(df_ohe.isnull().sum()) X = X.drop(columns=['Gender', 'Education Level']) display(X) print(X.isnull().sum()) X = X.join(df_ohe) print(X.isnull().sum())
原因分析
join()方法默认按索引合并,当df_ohe的索引与X的索引无法完全匹配时,就会产生缺失值。ColumnTransformer.fit_transform()返回的稀疏矩阵转成DataFrame时,默认生成从0开始的连续整数索引;而X经过dropna()操作后,索引可能变成不连续状态,两者索引无法对齐,合并后就会出现NaN。
更安全的合并方法
方法1:对齐索引后合并
创建df_ohe时直接设置其索引与X一致,确保合并时索引完全匹配:
# 生成独热编码DataFrame时指定索引 df_ohe = pd.DataFrame(transformed, columns=columns, index=X.index) # 删除原分类列并合并 X = X.drop(columns=['Gender', 'Education Level']) X = X.join(df_ohe)
方法2:用ColumnTransformer直接保留其他列(推荐)
无需手动拆分和合并,让ColumnTransformer自动保留不需要编码的列,一步完成特征处理:
myTransformer = ColumnTransformer( transformers=[ ('one_hot_encoder', OneHotEncoder(), ['Gender', 'Education Level']) ], remainder='passthrough' # 保留未指定的列(Age、Years of Experience) ) # 生成处理后的完整特征矩阵并转成DataFrame transformed_full = myTransformer.fit_transform(X) # 整理所有列名 all_columns = (myTransformer.named_transformers_['one_hot_encoder'].get_feature_names_out(['Gender', 'Education Level']).tolist() + [col for col in X.columns if col not in ['Gender', 'Education Level']]) X_processed = pd.DataFrame(transformed_full, columns=all_columns, index=X.index)
内容的提问来源于stack exchange,提问作者camdenmcgath
相关产品推荐
相关产品推荐

