Пакетный градиентный спуск с scikit learn (склеарн)

Я играю с классификатором "Логистическая регрессия один-на-все", используя Scikit-Learn (sklearn). У меня есть большой набор данных, который слишком медленный, чтобы запускать все сразу; Также я хотел бы изучить кривую обучения в процессе обучения.

Я хотел бы использовать пакетный градиентный спуск, чтобы обучить мой классификатор партиями, скажем, 500 образцов. Есть ли какой-нибудь способ использования sklearn для этого, или я должен отказаться от sklearn и "бросить свой собственный"?

Это то, что я до сих пор:

from sklearn.linear_model import LogisticRegression
from sklearn.multiclass import OneVsRestClassifier

# xs are subsets of my training data, ys are ground truth for same; I have more 
# data available for further training and cross-validation:
xs.shape, ys.shape
# => ((500, 784), (500))
lr = OneVsRestClassifier(LogisticRegression())
lr.fit(xs, ys)
lr.predict(xs[0,:])
# => [ 1.]
ys[0]
# => 1.0

Т.е. он правильно идентифицирует тренировочный образец (да, я понимаю, что было бы лучше оценить его с новыми данными - это всего лишь быстрая дымовая проверка).

Повторный градиентный спуск: я не дошел до создания кривых обучения, но можно просто запустить fit повторно на последующих подмножествах обучающих данных? Или есть какая-то другая функция для обучения в партиях? Документация и Google довольно молчат по этому вопросу. Спасибо!

1 ответ

Решение

То, что вы хотите, это не пакетный градиентный спуск, а стохастический градиентный спуск; Пакетное обучение означает обучение всему обучающему набору за один раз, в то время как то, что вы описываете, правильно называется миниатюрным обучением. Это реализовано в sklearn.linear_model.SGDClassifier, которая соответствует модели логистической регрессии, если вы даете ей возможность loss="log",

С SGDClassifierкак с LogisticRegressionнет необходимости оборачивать оценщик в OneVsRestClassifier - оба проводят тренировку "один против всех" из коробки.

# you'll have to set a few other options to get good estimates,
# in particular n_iterations, but this should get you going
lr = SGDClassifier(loss="log")

Затем, чтобы тренироваться на миниатчах, используйте partial_fit метод вместо fit, В первый раз вы должны передать ему список классов, потому что не все классы могут присутствовать в каждом мини-пакете:

import numpy as np
classes = np.unique(["ham", "spam", "eggs"])

for xs, ys in minibatches:
    lr.partial_fit(xs, ys, classes=classes)

(Здесь я прохожу classes для каждого мини-пакета, который не является необходимым, но не наносит вреда и делает код короче.)

Другие вопросы по тегам