如何从LogisticRegressionCV和GridSearchCV中获得可比较和可重复的结果

14

我想用不同的参数来评估不同的分类器。

为了加快LogisticRegression的速度,我使用LogisticRegressionCV(至少快2倍),并计划对其他分类器使用GridSearchCV

但是问题在于它给了我相等的C参数,但没有AUC ROC得分。

我将尝试修复许多参数,例如scorerrandom_statesolvermax_itertol...

请参考以下示例(实际数据没有关系):

测试数据和常见部分:

from sklearn import datasets
boston = datasets.load_boston()
X = boston.data
y = boston.target
y[y <= y.mean()] = 0; y[y > 0] = 1

import numpy as np
from sklearn.cross_validation import KFold
from sklearn.linear_model import LogisticRegression
from sklearn.grid_search import GridSearchCV
from sklearn.linear_model import LogisticRegressionCV

fold = KFold(len(y), n_folds=5, shuffle=True, random_state=777)

网格搜索

grid = {
    'C': np.power(10.0, np.arange(-10, 10))
     , 'solver': ['newton-cg']
}
clf = LogisticRegression(penalty='l2', random_state=777, max_iter=10000, tol=10)
gs = GridSearchCV(clf, grid, scoring='roc_auc', cv=fold)
gs.fit(X, y)

print ('gs.best_score_:', gs.best_score_)

gs.best_score_: 0.939162082194

LogisticRegressionCV

searchCV = LogisticRegressionCV(
    Cs=list(np.power(10.0, np.arange(-10, 10)))
    ,penalty='l2'
    ,scoring='roc_auc'
    ,cv=fold
    ,random_state=777
    ,max_iter=10000
    ,fit_intercept=True
    ,solver='newton-cg'
    ,tol=10
)
searchCV.fit(X, y)

print ('Max auc_roc:', searchCV.scores_[1].max())

最大auc_roc值为0.970588235294

solver参数中使用了newton-cg,其余也进行了尝试。我忘了什么?

P.S. 在这两种情况下,我还收到了警告信息 "/usr/lib64/python3.4/site-packages/sklearn/utils/optimize.py:193: UserWarning: Line Search failed warnings.warn('Line Search failed')",我也不理解它的含义。如果有人可以解释一下它的含义,我会很高兴,但我希望它与我的主要问题无关。

编辑更新

根据@joeln的评论,还需要添加max_iter=10000tol=10参数。这不会在任何位数上改变结果,但警告消失了。


1
为了确保,您能否减小 tol 并将相同的大 max_iter 提供给 LogisticRegression?如果它们正在解决相同的方程并到达不同的最小值,那么可能是因为搜索停止得太早了。 - joeln
谢谢。我添加了max_iter=10000和tol=10(不确定其含义)并纠正了问题。它没有改变任何数字的结果。 - Hubbitus
抱歉关于tol值的问题。您建议使用什么值?不幸的是,我是一个机器学习新手,也不确定...关于数据方面-我的问题示例特别基于嵌入在sklearn波士顿房屋演示值中,并且完全可重现!因此,我期望任何人只需复制,粘贴并运行它,都应该收到完全相同的结果。 - Hubbitus
1
哈哈,抱歉我没有注意到你是如何从“LogisticRegressionCV”中打印分数的。这似乎是错误的主要来源。 - joeln
@joeln 如果你愿意回答这个问题,并总结错误和评论答案,那么我会接受它。 - Hubbitus
显示剩余6条评论
1个回答

10

这是 scikit-learn 问题跟踪器上 Tom 的回答 的副本:

LogisticRegressionCV.scores_ 给出所有折叠的得分。 GridSearchCV.best_score_ 给出所有折叠中最佳平均得分。

要获得相同的结果,您需要更改代码:

print('Max auc_roc:', searchCV.scores_[1].max())  # is wrong
print('Max auc_roc:', searchCV.scores_[1].mean(axis=0).max())  # is correct

如果我使用默认的tol=1e-4而不是你的tol=10,那么结果如下:

('gs.best_score_:', 0.939162082193857)
('Max auc_roc:', 0.93915947999923843)

(小)剩余的差异可能来自于在LogisticRegressionCV中的热启动(实际上这就是使其比GridSearchCV 更快的原因)。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接