如何将多模型predict_proba输出整合为DataFrame供ML模型学习ensemble权重
多模型输出合并与自动权重学习集成实现方案
1. 合并多模型预测概率为输入特征
你现在每个基模型输出的是形状为(样本数, 类别数)的概率数组,直接按列拼接即可得到可喂给下游ML算法的特征:
import numpy as np import pandas as pd # 把所有基模型的预测结果放进列表 pred_list = [preds1, preds2] # 有更多模型直接加进列表即可 # 方法1:直接生成numpy特征矩阵,可直接输入ML模型 # 拼接后形状为(样本数, 模型数*类别数),比如2个4分类模型输出拼接后为(样本数,8) stacked_features = np.hstack(pred_list) # 方法2:转为DataFrame方便查看和后续处理 col_names = [] for model_id in range(len(pred_list)): for class_id in range(pred_list[0].shape[1]): col_names.append(f"model_{model_id+1}_class_{class_id+1}_prob") stacked_df = pd.DataFrame(stacked_features, columns=col_names)
2. 自动学习权重的正确实现方式
你当前手动遍历权重的方案属于固定线性加权,只能覆盖简单的融合规则,推荐使用*堆叠泛化(Stacking)*方案,通过元学习器自动学习最优融合权重,注意要避免数据泄露,不能直接用测试集预测结果训练元模型:
from sklearn.model_selection import KFold from sklearn.linear_model import LogisticRegression from sklearn.neighbors import KNeighborsClassifier from sklearn.metrics import accuracy_score # 配置项 base_models = [ # 基模型列表,可任意添加其他模型 LogisticRegression(random_state=42), KNeighborsClassifier(n_neighbors=5, metric='minkowski', p=2) ] n_folds = 5 # 交叉验证折数 n_classes = 4 # 你的场景是4分类 meta_model = LogisticRegression(random_state=42) # 元学习器,可替换为XGBoost等任意分类器 # 步骤1:生成训练集元特征(用交叉验证离群预测避免数据泄露) kf = KFold(n_splits=n_folds, shuffle=True, random_state=42) train_meta = np.zeros((xx_train.shape[0], len(base_models)*n_classes)) for model_idx, model in enumerate(base_models): for train_fold_idx, val_fold_idx in kf.split(xx_train): # 用训练折拟合基模型,预测验证折概率作为元特征 x_tr, x_val = xx_train[train_fold_idx], xx_train[val_fold_idx] y_tr = yy_train[train_fold_idx] model.fit(x_tr, y_tr) train_meta[val_fold_idx, model_idx*n_classes : (model_idx+1)*n_classes] = model.predict_proba(x_val) # 全量训练集拟合基模型,用于后续测试集预测 model.fit(xx_train, yy_train) # 步骤2:训练元学习器自动学习权重 meta_model.fit(train_meta, yy_train) # 步骤3:生成测试集元特征,得到最终预测结果 test_meta = np.zeros((xx_test.shape[0], len(base_models)*n_classes)) for model_idx, model in enumerate(base_models): test_meta[:, model_idx*n_classes : (model_idx+1)*n_classes] = model.predict_proba(xx_test) final_preds = meta_model.predict(test_meta) print(f"集成模型准确率:{accuracy_score(yy_test, final_preds):.4f}")
如果你不需要自定义逻辑,也可以直接用sklearn封装好的StackingClassifier接口,一行即可完成上述所有流程。
内容的提问来源于stack exchange,提问作者Parth Sharma
相关产品推荐
相关产品推荐

