当random_state为None时,StratifiedShuffleSplit函数(scikit-learn)的结果不同

时间:2014-04-03 15:55:24

标签: python random machine-learning scikit-learn cross-validation

我正在执行交叉验证以便正确分类。首先,我使用scikit-learn中的StratifiedKfold函数。在某些时候,我想进行更多迭代,然后我改为StratifiedShuffleSplit。通过这个新功能,我获得的结果发生了变化。最后,我意识到如果我指定一个random_state,我会再次获得与使用StratifiedKfold作为CV时获得的结果类似的结果。

总之,如果我指定random_state,对于不同的值,我会得到稍微不同的结果,类似于我使用StratifiedKfold获得的结果(一次迭代,或者我自己计算洗牌,如here)。但是,如果random_state为none或未指定,则我获得的结果完全改变。

我检查了当random_state为None时,列车和测试索引是不同的,并按预期分层。

我没有使用随机数生成器的经验,但这对我没有任何意义

查看代码我意识到当random_state为None时,调用函数check_random_state。此函数,如果seed为none,则返回np.random(link)使用的RandomState单例。

我写了一些有问题的代码。 如果我用下面的那个更改注释行,我会得到不同的结果。

import numpy as np
import sklearn as skl

(...)
#skCVs=skl.cross_validation.StratifiedShuffleSplit(classes,n_iter=iterations*kfoldCV,test_size = 1/float(kfoldCV),random_state=5)
skCVs=skl.cross_validation.StratifiedShuffleSplit(classes,n_iter=iterations*kfoldCV,test_size = 1/float(kfoldCV))

for train,test in skCVs:

   (classification, ...)

我使用的是sklearn版本0.14。

你有任何解释或线索可以帮助理解正在发生的事情吗?

2 个答案:

答案 0 :(得分:5)

(分层)ShuffleSplit在分割之前随机抽取数据。 (伪)随机性由random_state构造函数参数控制。默认的None值意味着每个新呼叫都会产生不同的混乱。要获得确定性的混洗,您可以选择传递整数种子。

答案 1 :(得分:1)

我也不是随机生成器的专家,但是我可以理解,如果你没有定义random_state,就会调用一个不同的RandomState类型。以下是我发现的解释:

“如果种子为无,则RandomState将尝试从/ dev / urandom(或Windows模拟)中读取数据(如果可用),或者从时钟读取种子。”[1]

“如果size是一个整数,则返回一个填充了生成值的一维数组。”[1]

你可以在这里看到“check_random_state”[2]中调用的两个不同随机生成器的代码。

[1] http://docs.scipy.org/doc/numpy/reference/generated/numpy.random.RandomState.html

[2] https://github.com/scikit-learn/scikit-learn/blob/0.14.X/sklearn/utils/validation.py

这对你有帮助吗?