我正在尝试在MultinomialNB上进行随机参数优化(1)。现在我的参数有3而不是一个值,因为它是'class_prior'而且我有3个类。
from sklearn.naive_bayes import MultinomialNB
from sklearn.grid_search import RandomizedSearchCV
from scipy.stats import uniform
tuned_parameters = {'class_prior': [uniform.rvs(0,3), uniform.rvs(0,3),
uniform.rvs(0,3)]}
clf = RandomizedSearchCV(MultinomialNB(), tuned_parameters, cv=3,
scoring='f1_micro', n_iter=10)
但错误日志如下所示:
...
File "/home/mark/Virtualenvs/python3env2/lib/python3.5/site-
packages/sklearn/naive_bayes.py", line 607, in fit
self._update_class_log_prior(class_prior=class_prior)
File "/home/mark/Virtualenvs/python3env2/lib/python3.5/site-
packages/sklearn/naive_bayes.py", line 455, in _update_class_log_prior
if len(class_prior) != n_classes:
TypeError: object of type 'numpy.float64' has no len()
还尝试删除.rvs - >
TypeError: object of type 'rv_frozen' has no len()
RandomizeSearch是不可能有一个包含3个组件的变量,即3个class_priors?
答案 0 :(得分:2)
是的,可能。这样做:
tuned_parameters = {'class_prior': [[uniform.rvs(0,3), uniform.rvs(0,3),
uniform.rvs(0,3)]]}
注意值周围的额外方括号。 原因是RandomizedSearchCV(或GridSearchCV)要调整的参数应该包含在一个列表中,每次都会尝试使用一个元素。将保留产生最高分数(或损失情况下最低分数)的元素组合。
例如,请参阅SVC参数调整的简单代码:
parameters = {'kernel':['linear', 'rbf'], 'C':[1, 10]}
这将扩展为总共4个值的排列,如下所示:
Option1:- 'kernel':'linear', 'C':1
Option2:- 'kernel':'linear', 'C':10
Option3:- 'kernel':'rbf', 'C':1
Option4:- 'kernel':'rbf', 'C':10
这意味着估算器将适合4次(每次使用上面的不同选项),然后将保留最佳估算器。
在您的情况下,根据documentation of MultinomialNB class_prior
,是类的概率数组。
理想情况下,它应该像这样扩展:
选项1:'class_prior':[uniform.rvs(0,3),uniform.rvs(0,3),uniform.rvs(0,3)]
但是在RandomizedSearhCV(没有关于class_prior类型的信息)中,它将被扩展为:
Option1: 'class_prior': uniform.rvs(0,3)
Option2: 'class_prior': uniform.rvs(0,3)
Option3: 'class_prior': uniform.rvs(0,3)
然后会将其呈现给MultinomialNB,因为uniform.rvs()
的输出是浮点数而不是列表,所以它不会有len()
因此错误。
为此,您需要使用双方括号,以便正确扩展,如下所示:
Option1: 'class_prior': [uniform.rvs(0,3), uniform.rvs(0,3), uniform.rvs(0,3)]
但现在也有问题。由于扩展产生了一个选项,所以很明显,无论得分如何都会被选中(因为我们没有任何其他选择)。
此外,RandomizedSearchCV会抛出错误,因为您指定了n_iter=10
,并且选择的数量应该多于(在我们的例子中,它是一个选择)。
所以你需要改变你的tuned_parameters
:
tuned_parameters = {'class_prior': [[uniform.rvs(0,3), uniform.rvs(0,3), uniform.rvs(0,3)],
[uniform.rvs(0,3), uniform.rvs(0,3), uniform.rvs(0,3)],
[uniform.rvs(0,3), uniform.rvs(0,3), uniform.rvs(0,3)],
[uniform.rvs(0,3), uniform.rvs(0,3), uniform.rvs(0,3)],
[uniform.rvs(0,3), uniform.rvs(0,3), uniform.rvs(0,3)],
...
...
... ]}
至少n_iter
次。