statsmodel中的MNLogit返回nan

我在尝试对著名的iris数据集使用statsmodels的MNLogit函数时,得到的结果是:“当前函数值:nan”。这是我使用的代码:

import statsmodels.api as stiris = st.datasets.get_rdataset('iris','datasets')y = iris.data.Speciesx = iris.data.ix[:, 0:4]x = st.add_constant(x, prepend = False)mdl = st.MNLogit(y, x)mdl_fit = mdl.fit()print (mdl_fit.summary())

回答:

在iris的例子中,我们可以完美预测Setosa。这在Logit和MNLogit中会导致(部分)完美分离的问题。

完美分离对于预测是有利的,但logit的参数会趋向于无穷。在这种情况下,我使用statsmodels的最新版本(在Windows上)时,得到的是奇异矩阵错误,而不是Nans。

离散模型的默认优化器是牛顿法,当Hessian矩阵变为奇异时会失败。其他不使用Hessian信息的优化器能够完成优化。例如,使用’bfgs’,我得到

>>> mdl_fit = mdl.fit(method='bfgs')Warning: 已超过最大迭代次数。         当前函数值:0.057112         迭代次数:35         函数评估次数:37         梯度评估次数:37e:\josef\eclipsegworkspace\statsmodels-git\statsmodels-all-new2_py27\statsmodels\statsmodels\base\model.py:471: ConvergenceWarning: 最大似然优化未能收敛。检查mle_retvals  "检查mle_retvals", ConvergenceWarning)

对于Setosa的预测概率基本上是(1, 0, 0),也就是说它们被完美预测

>>> fitted = mdl_fit.predict()>>> fitted[y=='setosa'].min(0)array([  9.99497636e-01,   2.07389867e-11,   1.71740822e-38])>>> fitted[y=='setosa'].max(0)array([  1.00000000e+00,   5.02363854e-04,   1.05778255e-20])

然而,由于完美分离,参数无法被识别,值主要由优化器的停止标准决定,标准误差非常大。

>>> print(mdl_fit.summary())                          MNLogit回归结果                          ==============================================================================因变量:                物种   观测数:                  150模型:                        MNLogit   残差自由度:                      140方法:                           最大似然估计   模型自由度:                            8日期:                2015年7月20日星期一   伪R平方:                  0.9480时间:                        04:08:04   对数似然:                -8.5668收敛:                      否   空模型对数似然:                       -164.79                                        LLR p值:                 9.200e-63=====================================================================================物种=versicolor       系数    标准误差          z      P>|z|      [95.0% 置信区间]--------------------------------------------------------------------------------------萼片长度          -1.4959    444.817     -0.003      0.997      -873.321   870.330萼片宽度           -8.0560    282.766     -0.028      0.977      -562.267   546.155花瓣长度          11.9301    374.116      0.032      0.975      -721.323   745.184花瓣宽度            1.7039    759.366      0.002      0.998     -1486.627  1490.035常数                  1.6444   1550.515      0.001      0.999     -3037.309  3040.597--------------------------------------------------------------------------------------物种=virginica       系数    标准误差          z      P>|z|      [95.0% 置信区间]-------------------------------------------------------------------------------------萼片长度         -8.0348    444.835     -0.018      0.986      -879.896   863.827萼片宽度         -15.8195    282.793     -0.056      0.955      -570.083   538.444花瓣长度         22.1797    374.155      0.059      0.953      -711.152   755.511花瓣宽度          14.0603    759.384      0.019      0.985     -1474.304  1502.425常数                -6.5053   1550.533     -0.004      0.997     -3045.494  3032.483=====================================================================================

关于statsmodels中的实现

Logit会专门检查完美分离,并引发一个可以选择性地减弱为警告的异常。对于其他模型如MNLogit,目前还没有明确的完美分离检查,主要是因为缺乏好的测试案例和容易识别的通用条件。(有几个问题如https://github.com/statsmodels/statsmodels/issues/516仍未解决)

我的总体策略:

当出现收敛失败时,尝试不同的优化器和不同的起始值(start_params)。如果某些优化器成功了,那么这可能是一个困难的优化问题,要么是目标函数的曲率,要么是解释变量的比例不当或类似情况。一个有用的检查是使用像nmpowell这样的鲁棒优化器的参数估计作为更严格的优化器(如newtonbfgs)的起始值。

如果在某些优化器收敛后结果仍然不好,那么这可能是数据本身的问题,如Logit、Probit和其他几个模型中的完美分离,或是设计矩阵的奇异或近似奇异。在这种情况下,必须更改模型。关于完美分离的建议可以通过互联网搜索找到。

Related Posts

L1-L2正则化的不同系数

我想对网络的权重同时应用L1和L2正则化。然而,我找不…

使用scikit-learn的无监督方法将列表分类成不同组别,有没有办法?

我有一系列实例,每个实例都有一份列表,代表它所遵循的不…

f1_score metric in lightgbm

我想使用自定义指标f1_score来训练一个lgb模型…

通过相关系数矩阵进行特征选择

我在测试不同的算法时,如逻辑回归、高斯朴素贝叶斯、随机…

可以将机器学习库用于流式输入和输出吗?

已关闭。此问题需要更加聚焦。目前不接受回答。 想要改进…

在TensorFlow中,queue.dequeue_up_to()方法的用途是什么?

我对这个方法感到非常困惑,特别是当我发现这个令人费解的…

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注