训练足球预测模型后,如何反转sklearn LabelEncoder的编码?
问题描述
用Python构建足球比赛结果预测模型时,使用sklearn.preprocessing.LabelEncoder对Home Team、Away Team、Match Result字段编码,训练完XGBClassifier后,生成的对比DataFrame里球队是编码值,无法还原为原始名称,尝试移除.values转DataFrame的方法无效,求解决办法。
附原核心代码:
features = ['Home Team',..., 'home_team_avg_Sh_last_3', 'Away Team',..., 'away_team_avg_Sh_last_3'] label = ['Match Result'] df_allteammerged[features + label] encode = ['Home Team', 'Away Team', 'Match Result'] from sklearn.preprocessing import LabelEncoder enc = LabelEncoder() for e in encode: df_allteammerged[e] = enc.fit_transform(df_allteammerged[e]) df_allteammerged[features + label] X = df_allteammerged[features].values y = df_allteammerged[label].values.flatten() from sklearn.model_selection import train_test_split X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.30, random_state=0) from xgboost import XGBClassifier model = XGBClassifier(objective="multi:softmax") model.fit(X_train,y_train) xgb_pred = model.predict(X_test) xtesthome = [i[0] for i in X_test] xtestaway = [i[9] for i in X_test] df_pred_compare = pd.DataFrame({"Actual Result": y_test, "Predicted Result": xgb_pred, "Home Team": xtesthome,"Away Team": xtestaway})
问题根源
原代码用同一个LabelEncoder实例循环处理三个字段,每次fit_transform都会覆盖编码器的类别映射关系,最终仅保留最后一个字段(Match Result)的映射,球队名称的编码映射已丢失,无法直接还原。
解决方案
1. 为每个字段单独保存编码器实例
为每个需要编码的字段创建独立的LabelEncoder,并将实例存入字典保留映射关系:
from sklearn.preprocessing import LabelEncoder # 为每个编码字段创建独立编码器并保存 encoders = {} encode_cols = ['Home Team', 'Away Team', 'Match Result'] for col in encode_cols: le = LabelEncoder() df_allteammerged[col] = le.fit_transform(df_allteammerged[col]) encoders[col] = le # 存储编码器,用于后续还原
2. 还原编码值到原始名称
方法一:直接还原现有对比DataFrame中的编码值
针对已生成的df_pred_compare,用对应编码器的inverse_transform方法还原:
# 还原球队名称 df_pred_compare['Home Team'] = encoders['Home Team'].inverse_transform(df_pred_compare['Home Team']) df_pred_compare['Away Team'] = encoders['Away Team'].inverse_transform(df_pred_compare['Away Team']) # 可选:同时还原比赛结果的编码值 df_pred_compare['Actual Result'] = encoders['Match Result'].inverse_transform(df_pred_compare['Actual Result']) df_pred_compare['Predicted Result'] = encoders['Match Result'].inverse_transform(df_pred_compare['Predicted Result'])
方法二:拆分数据集时保留DataFrame结构,直接关联还原
拆分训练测试集时不转为数组,保留DataFrame结构,生成对比表时直接用编码器还原:
# 拆分时保留DataFrame格式 X = df_allteammerged[features] y = df_allteammerged[label].values.flatten() X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.30, random_state=0) # 训练模型(代码不变) model = XGBClassifier(objective="multi:softmax") model.fit(X_train,y_train) xgb_pred = model.predict(X_test) # 生成对比表时直接还原编码值 df_pred_compare = pd.DataFrame({ "Actual Result": encoders['Match Result'].inverse_transform(y_test), "Predicted Result": encoders['Match Result'].inverse_transform(xgb_pred), "Home Team": encoders['Home Team'].inverse_transform(X_test['Home Team']), "Away Team": encoders['Away Team'].inverse_transform(X_test['Away Team']) })
3. 注意事项
- 禁止用同一个
LabelEncoder处理多个不同字段,避免映射关系被覆盖。 - 若需保存模型用于后续部署,需同时用
pickle保存encoders字典,确保部署时能正常还原编码值。
内容的提问来源于stack exchange,提问作者Andreas Wong
相关产品推荐
相关产品推荐

