Потеря поезда и потеря проверки GradientBoostingClassifier - PullRequest
0 голосов
/ 26 мая 2018

Я учусь делать классификацию для данных типа покрытия для 7 классов.Я тренирую свою модель с GradientBoostingClassifier из scikit-learn.Когда я пытаюсь построить свою функцию потерь, это выглядит так:

enter image description here

Показывает ли этот вид графика, что моя модель страдает от высокой дисперсии?Если да, что мне делать?И я не знаю, почему в середине итераций от 200 до 500 график имеет форму прямоугольника.

(РЕДАКТИРОВАТЬ) Чтобы редактировать этот пост, я не уверен, чтонеправильно с моим кодом, потому что я просто использовал обычный код, чтобы соответствовать обучающим даннымЯ использую ноутбук Jupyter.Так что я просто собираюсь предоставить код

Y = train["Cover_Type"]
X = train.drop({"Cover_Type"}, axis=1) 

#split training data dan cross validation
from sklearn.model_selection import train_test_split

X_train, X_val, Y_train, Y_val = train_test_split(X,Y,test_size=0.3,random_state=42)

from sklearn.metrics import mean_squared_error
from sklearn.datasets import make_friedman1
from sklearn.ensemble import GradientBoostingClassifier

params = {'n_estimators': 1000,'learning_rate': 0.3, 'max_features' : 'sqrt'}

dtree=GradientBoostingClassifier(**params)
dtree.fit(X_train,Y_train)

#mau lihat F1-Score
from sklearn.metrics import f1_score

Y_pred = dtree.predict(X_val) #prediksi data cross validation menggunakan model tadi
print Y_pred
score = f1_score(Y_val, Y_pred, average="micro") 

print("Gradient Boosting Tree F1-score: "+str(score)) # I got 0.86 F1-Score

import matplotlib.pyplot as plt
# Plot training deviance

# compute test set deviance
val_score = np.zeros((params['n_estimators'],), dtype=np.float64)

for i, Y_pred in enumerate(dtree.staged_predict(X_val)):
    val_score[i] = dtree.loss_(Y_val, Y_pred.reshape(-1, 1))

plt.figure(figsize=(12, 6))
plt.subplot(1, 2, 1)
plt.title('Deviance')
plt.plot(np.arange(params['n_estimators']) + 1, dtree.train_score_, 'b-',
             label='Training Set Deviance')
plt.plot(np.arange(params['n_estimators']) + 1, val_score, 'r-',
             label='Validation Set Deviance')
plt.legend(loc='upper right')
plt.xlabel('Boosting Iterations')
plt.ylabel('Deviance')

Ответы [ 2 ]

0 голосов
/ 10 апреля 2019

Есть несколько вопросов, которые я объясню по одному, а также я добавил правильный код для вашего примера.

  1. staged_predict(X) метод НЕ должен использоваться

    • Поскольку staged_predict(X) выводит прогнозируемый класс вместо прогнозируемых вероятностей, использование этого неверно.
    • Можно (если контекст принимает) использовать staged_decision_function(X) метод и передавать вычисленные решения на каждом этапе в атрибут model.loss_.Но в этом примере он не работает (потери на основе поэтапного решения увеличиваются, а потери уменьшаются).
  2. Вы должны использоватьstaged_predict_proba(X) с кросс-энтропийной потерей

    • вы должны использовать staged_predict_proba(X)
    • , вам также необходимо определить функцию, которая рассчитывает кросс-энтропийную потерю на каждом этапе.
    • Я предоставил код ниже.Обратите внимание, что я установил для многословия значение 2, а затем вы можете видеть, что потери на тренировке склеарна на каждом этапе совпадают с нашей потерей (в качестве проверки работоспособности, что наш подход работает правильно).
  3. Почему у вас большие прыжки

    • Я думаю, причина в том, что GBC становится очень уверенным, а затем предсказывает, что метка равна 1 (в качестве примера) с вероятностью один , хотя это не правильно (например, метка 2).Это создает большие скачки (так как перекрестная энтропия уходит в бесконечность).В таком случае вам следует изменить параметры GBC.
  4. Код и график приведены ниже

    • код:
import numpy as np
import matplotlib.pyplot as plt
from sklearn.datasets import fetch_covtype
from sklearn.model_selection import train_test_split
from sklearn.ensemble import GradientBoostingClassifier


def _cross_entropy_like_loss(model, input_data, targets, num_estimators):
    loss = np.zeros((num_estimators, 1))
    for index, predict in enumerate(model.staged_predict_proba(input_data)):
        loss[index, :] = -np.sum(np.log([predict[sample_num, class_num-1]
                                         for sample_num, class_num in enumerate(targets)])) 
        print(f'ce loss {index}:{loss[index, :]}')
    return loss


covtype = fetch_covtype()
X = covtype.data
Y = covtype.target
n_estimators = 10
X_train, X_val, Y_train, Y_val = train_test_split(X, Y, test_size=0.3, random_state=42)
clf = GradientBoostingClassifier(n_estimators=n_estimators, learning_rate=0.3, verbose=2 )
clf.fit(X_train, Y_train)


tr_loss_ce = _cross_entropy_like_loss(clf, X_train, Y_train, n_estimators)
test_loss_ce = _cross_entropy_like_loss(clf, X_val, Y_val, n_estimators)


plt.figure()
plt.plot(np.arange(n_estimators) + 1, tr_loss_ce, '-r', label='training_loss_ce')
plt.plot(np.arange(n_estimators) + 1, test_loss_ce, '-b', label='val_loss_ce')
plt.ylabel('Error')
plt.xlabel('num_components')
plt.legend(loc='upper right')
  • Вывод консоли аналогичен приведенному ниже, из которого можно легко проверить правильность подхода.
     Iter       Train Loss   Remaining Time 
         1      482434.6631            1.04m
         2      398501.7223           55.56s
         3      351391.6893           48.51s
         4      322290.3230           41.60s
         5      301887.1735           34.65s
         6      287438.7801           27.72s
         7      276109.2008           20.82s
         8      268089.2418           13.84s
         9      261372.6689            6.93s
        10      256096.1205            0.00s
ce loss 0:[ 482434.6630936]
ce loss 1:[ 398501.72228276]
ce loss 2:[ 351391.68933547]
ce loss 3:[ 322290.32300604]
ce loss 4:[ 301887.17346783]
ce loss 5:[ 287438.7801033]
ce loss 6:[ 276109.20077844]
ce loss 7:[ 268089.2418214]
ce loss 8:[ 261372.66892149]
ce loss 9:[ 256096.1205235]
0 голосов
/ 26 мая 2018

Кажется, у вас есть несколько проблем.Трудно сказать наверняка, потому что вы не предоставляете никакого кода.

Моя модель страдает от высокой дисперсии?

Во-первых, ваша модель с самого начала перегружена .Вы можете сказать, что это так, потому что ваша потеря проверки увеличивается, хотя ваша подготовка уменьшается.Интересно то, что с самого начала ваши потери при проверке возрастают, что говорит о том, что ваша модель не работает.Поэтому, чтобы ответить на ваш вопрос, да, он страдает от высокой дисперсии.

Что мне делать?

Вы уверены, что в ваших данных есть тенденция?Тот факт, что проверка увеличивается с самого начала , указывает на то, что либо эта модель вообще не применяется к вашим данным, что у ваших данных нет тенденции, либо что у вас есть проблемы с вашим кодом.Возможно, попробуйте другие модели и убедитесь, что ваш код правильный.Опять же, трудно сказать без минимального примера 1014 *.

Странный прямоугольник

Это выглядит странно.Либо есть проблема с вашими данными в наборе проверки (потому что это влияние не происходит на наборе проверки), либо у вас просто проблема с вашим кодом.Если вы предоставите образец, мы могли бы помочь вам больше.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...