【问题标题】:How to use a custom scoring function in GridSearchCV for unsupervised learning如何在 GridSearchCV 中使用自定义评分函数进行无监督学习
【发布时间】:2022-11-02 07:43:27
【问题描述】:

我想对一组超参数进行网格搜索以调整聚类模型。 GridSearchCV 为无监督学习提供了一堆评分函数,但我想使用一个不存在的函数,例如silhouette score

关于如何实现我的自定义函数的documentation 不清楚我们应该如何定义我们的评分函数。此处的示例显示了简单地导入自定义记分器并使用make_scorer 创建自定义记分函数。但是,make_scorer 似乎需要真实值(在无监督学习中不存在),因此不清楚如何使用它。

这是我到目前为止所拥有的:

from sklearn.datasets import make_blobs
from sklearn.model_selection import GridSearchCV
from sklearn.cluster import DBSCAN
from sklearn.metrics import silhouette_score, make_scorer

Z, _ = make_blobs()

gs = GridSearchCV(estimator=DBSCAN(), 
                  param_grid={'n_clusters': range(2, 5)}, 
                  cv=5, 
                  scoring=make_scorer(my_custom_function)
                 )
gs.fit(Z)

我尝试以各种方式编写my_custom_function,但收到如下警告或错误:

TypeError: __call__() missing 1 required positional argument: 'y_true'

或者

ValueError: Found input variables with inconsistent numbers of samples: [20, 80]

如何正确定义我的自定义评分函数?

【问题讨论】:

    标签: python machine-learning scikit-learn cluster-analysis grid-search


    【解决方案1】:

    你的模型必须有一个.fit_predict() 方法来获取标签。然后你的记分器函数必须返回一个值越大越好1. scikit-learn 上的所有聚类算法都实现了.fit_predict(),所以这方面没有问题。

    例如,要将剪影分数作为 DBSCAN 的评分指标,请按如下方式定义,并将其作为评分参数直接传递给 GridSearchCV。请注意,如果只有一个标签,剪影分数将无法正常工作,因此我们需要对此进行检查。

    def my_silhouette_score(model, X, y=None):
        preds = model.fit_predict(X)
        return silhouette_score(X, preds) if len(set(preds)) > 1 else float('nan')
    
    
    model = DBSCAN()
    pgrid = {
        'eps': np.linspace(0.01, 0.5, 10),
        'min_samples': np.arange(2, 10)
    }
    
    gs = GridSearchCV(model, pgrid, scoring=my_silhouette_score).fit(Z)
    best_estimator = gs.best_estimator_
    highest_silhouette_score = gs.score(Z)
    

    1:这真的不是问题;简单地改变结果的符号应该使函数最小化或最大化。

    【讨论】:

      猜你喜欢
      • 2022-10-25
      • 2014-04-20
      • 2019-02-08
      • 2013-03-24
      • 2017-12-08
      • 2019-02-20
      • 2015-06-01
      • 2016-08-24
      相关资源
      最近更新 更多