如何将经过培训的朴素贝叶斯分类器保存到磁盘并将其用于预测数据?
我从scikit-learn网站获得以下示例程序:
from sklearn import datasets
iris = datasets.load_iris()
from sklearn.naive_bayes import GaussianNB
gnb = GaussianNB()
y_pred = gnb.fit(iris.data, iris.target).predict(iris.data)
print "Number of mislabeled points : %d" % (iris.target != y_pred).sum()
答案 0 :(得分:191)
您还可以使用joblib.dump和joblib.load,它比默认的python pickler更有效地处理数值数组。
Joblib包含在scikit-learn中:
>>> from sklearn.externals import joblib
>>> from sklearn.datasets import load_digits
>>> from sklearn.linear_model import SGDClassifier
>>> digits = load_digits()
>>> clf = SGDClassifier().fit(digits.data, digits.target)
>>> clf.score(digits.data, digits.target) # evaluate training error
0.9526989426822482
>>> filename = '/tmp/digits_classifier.joblib.pkl'
>>> _ = joblib.dump(clf, filename, compress=9)
>>> clf2 = joblib.load(filename)
>>> clf2
SGDClassifier(alpha=0.0001, class_weight=None, epsilon=0.1, eta0=0.0,
fit_intercept=True, learning_rate='optimal', loss='hinge', n_iter=5,
n_jobs=1, penalty='l2', power_t=0.5, rho=0.85, seed=0,
shuffle=False, verbose=0, warm_start=False)
>>> clf2.score(digits.data, digits.target)
0.9526989426822482
答案 1 :(得分:176)
分类器只是可以像其他任何一样进行酸洗和转储的对象。继续你的例子:
import cPickle
# save the classifier
with open('my_dumped_classifier.pkl', 'wb') as fid:
cPickle.dump(gnb, fid)
# load it again
with open('my_dumped_classifier.pkl', 'rb') as fid:
gnb_loaded = cPickle.load(fid)
答案 2 :(得分:86)
您要查找的内容在留言单词中称为模型持久性,并在introduction和model persistence部分中进行了记录。
所以你已经初始化了你的分类器并用
训练了很长时间clf = some.classifier()
clf.fit(X, y)
在此之后,您有两个选择:
1)使用Pickle
import pickle
# now you can save it to a file
with open('filename.pkl', 'wb') as f:
pickle.dump(clf, f)
# and later you can load it
with open('filename.pkl', 'rb') as f:
clf = pickle.load(f)
2)使用Joblib
from sklearn.externals import joblib
# now you can save it to a file
joblib.dump(clf, 'filename.pkl')
# and later you can load it
clf = joblib.load('filename.pkl')
再一次阅读上述链接是有帮助的
答案 3 :(得分:25)
在许多情况下,特别是文本分类仅仅存储分类器是不够的,但您也需要存储矢量图,以便将来可以对输入进行矢量化。
import pickle
with open('model.pkl', 'wb') as fout:
pickle.dump((vectorizer, clf), fout)
未来的用例:
with open('model.pkl', 'rb') as fin:
vectorizer, clf = pickle.load(fin)
X_new = vectorizer.transform(new_samples)
X_new_preds = clf.predict(X_new)
在转储矢量图之前,可以通过以下方法删除矢量化程序的stop_words_属性:
vectorizer.stop_words_ = None
使转储效率更高。 此外,如果您的分类器参数是稀疏的(如在大多数文本分类示例中),您可以将参数从密集转换为稀疏,这将在内存消耗,加载和转储方面产生巨大差异。 Sparsify模型:
clf.sparsify()
哪个会自动适用于SGDClassifier但是如果您知道您的模型稀疏(clf.coef_中有很多零),那么您可以手动将clf.coef_转换为csr scipy sparse matrix:
clf.coef_ = scipy.sparse.csr_matrix(clf.coef_)
然后您可以更有效地存储它。
答案 4 :(得分:3)
sklearn
估算器实现了一些方法,可以让您轻松保存估算器的相关训练属性。一些估算器本身实现了__getstate__
方法,但是其他方法,例如GMM
只使用base implementation,它只是保存对象内部字典:
def __getstate__(self):
try:
state = super(BaseEstimator, self).__getstate__()
except AttributeError:
state = self.__dict__.copy()
if type(self).__module__.startswith('sklearn.'):
return dict(state.items(), _sklearn_version=__version__)
else:
return state
将模型保存到光盘的建议方法是使用pickle
模块:
from sklearn import datasets
from sklearn.svm import SVC
iris = datasets.load_iris()
X = iris.data[:100, :2]
y = iris.target[:100]
model = SVC()
model.fit(X,y)
import pickle
with open('mymodel','wb') as f:
pickle.dump(model,f)
但是,您应该保存其他数据,以便将来重新训练您的模型,或遭受可怕的后果(例如被锁定在旧版本的sklearn中)。
为了使用未来版本重建类似的模型 scikit-learn,应该沿着pickled保存额外的元数据 型号:
训练数据,例如对不可变快照的引用
用于生成模型的python源代码
scikit-learn及其依赖项的版本
在训练数据上获得的交叉验证分数
对于依赖于用Cython编写的tree.pyx
模块(例如IsolationForest
)的Ensemble估算器尤其如此,因为它创建了与实现的耦合,不保证在sklearn版本之间保持稳定。它在过去看到了倒退不兼容的变化。
如果您的模型变得非常大并且加载变得令人讨厌,您也可以使用效率更高的joblib
。来自文档:
在scikit的特定情况下,使用它可能更有趣 joblib取代
pickle
(joblib.dump
&joblib.load
),这是 在内部携带大型numpy数组的对象上效率更高 通常情况下适合的scikit-learn估算器,但只能 pickle到磁盘而不是字符串:
答案 5 :(得分:1)
sklearn.externals.joblib
自0.21
起已弃用,并将在v0.23
中删除:
/usr/local/lib/python3.7/site-packages/sklearn/externals/joblib/ init .py:15: FutureWarning:sklearn.externals.joblib在0.21中已弃用,并且将 在0.23中删除。请直接从导入此功能 joblib,可以通过以下方式安装:pip install joblib。如果这 加载腌制模型时出现警告,您可能需要 使用scikit-learn 0.21+重新序列化这些模型。
warnings.warn(msg,category = FutureWarning)
因此,您需要安装joblib
:
pip install joblib
最后将模型写入磁盘:
import joblib
from sklearn.datasets import load_digits
from sklearn.linear_model import SGDClassifier
digits = load_digits()
clf = SGDClassifier().fit(digits.data, digits.target)
with open('myClassifier.joblib.pkl', 'wb') as f:
joblib.dump(clf, f, compress=9)
现在要读取转储文件,您需要运行的是:
with open('myClassifier.joblib.pkl', 'rb') as f:
my_clf = joblib.load(f)