使用 GridSearchCV 进行分类阈值调整

数据挖掘 scikit-学习 超参数调整
2022-02-22 18:36:26

在 Scikit-learn 中,GridSearchCV 可用于根据参数网格验证模型。针对某些 DecisionTreeClassifier 参数的网格搜索 cv 的简短示例如下所示:

model = DecisionTreeClassifier()
params = [{'criterion':["gini","entropy"],"max_depth":[1,2,3,4,5,6,7,8,9,10],"class_weight":["balanced"]}]
GSCV = GridSearchCV(model,params,scoring="f1_micro")
GSCV.fit(X_train,y_train)
GSCV.best_params_

现在,我只关心二进制分类。对于许多算法来说,它们计算一个概率分数,并将决策阈值设置为 0.5。我的问题如下:如果我想将决策阈值视为网格搜索的另一个参数(以及现有参数),是否有使用 GridSearchCV 执行此操作的标准方法?例如,以下 tunegrid 中的最后一个参数“decision_threshold”之类的东西是理想的:

params = [{'criterion':["gini","entropy"],"max_depth":[1,2,3,4,5,6,7,8,9,10],"class_weight":["balanced"], "decision_threshold": [0.1,0.2,...,0.9]}]

不用说,我对仅适用于 DecisionTreeClassifier 的特定解决方案不感兴趣。相反,任何使用可以调整的概率决策阈值的分类器的通用解决方案。最好,如果可能的话,我想保留我当前的 GridSearchCV。

1个回答

据我所知,您不能将模型的阈值添加为超参数,但要找到最佳阈值,您可以执行以下操作:

  1. 制定标准GridSearchCV,但roc_auc按照步骤 2 使用 as 指标

     model = DecisionTreeClassifier()
     params = [{'criterion':["gini","entropy"],"max_depth":[1,2,3,4,5,6,7,8,9,10],"class_weight":["balanced"]}]
     GSCV = GridSearchCV(model,params,scoring="roc_auc")
     GSCV.fit(X_train,y_train)
     GSCV.best_params_
     best_model = GSCV.best_estimator_
    
  2. 一旦你设置了最好的超参数,你可以获得最大化 roc 曲线的阈值,如下所示:

     from sklearn.metrics import roc_curve
     preds = best_model.predict_proba(X_train)[:,1]
    
     fpr, tpr, thresholds = roc_curve(y_train, preds)
     optimal_idx = np.argmax(tpr - fpr)
     optimal_threshold = thresholds[optimal_idx]
    

此阈值将为您提供最低的误报率和最高的真阳性率