Ta strona została przetłumaczona przez Cloud Translation API.
Switch to English

Wzmocniono drzewa za pomocą estymatorów

Zobacz na TensorFlow.org Uruchom w Google Colab Wyświetl źródło na GitHub Pobierz notatnik

Ten samouczek jest kompleksowym instruktażem szkolenia modelu Gradient Boosting przy użyciu drzew decyzyjnych za pomocą interfejsu API tf.estimator . Modele drzew wzmocnionych należą do najpopularniejszych i najbardziej skutecznych metod uczenia maszynowego zarówno w przypadku regresji, jak i klasyfikacji. Jest to technika zespołowa, która łączy przewidywania z kilku (na przykład 10, 100 lub nawet 1000) modeli drzewiastych.

Modele Boosted Trees są popularne wśród wielu praktyków uczenia maszynowego, ponieważ mogą osiągnąć imponującą wydajność przy minimalnym dostrajaniu hiperparametrów.

Załaduj zestaw danych Titanic

Będziesz używać tytanicznego zbioru danych, którego (raczej chorobliwym) celem jest przewidywanie przeżycia pasażerów, biorąc pod uwagę cechy takie jak płeć, wiek, klasa itp.

 import numpy as np
import pandas as pd
from IPython.display import clear_output
from matplotlib import pyplot as plt

# Load dataset.
dftrain = pd.read_csv('https://storage.googleapis.com/tf-datasets/titanic/train.csv')
dfeval = pd.read_csv('https://storage.googleapis.com/tf-datasets/titanic/eval.csv')
y_train = dftrain.pop('survived')
y_eval = dfeval.pop('survived')
 
 import tensorflow as tf
tf.random.set_seed(123)
 

Zbiór danych składa się ze zbioru uczącego i zbioru ewaluacyjnego:

  • dftrain i y_train to zbiór y_train - dane, których model używa do nauki.
  • Model jest testowany względem zbioru eval , dfeval i y_eval .

Podczas treningu będziesz korzystać z następujących funkcji:

Nazwa funkcji Opis
seks Płeć pasażera
wiek Wiek pasażera
n_siblings_spouses rodzeństwo i partnerzy na pokładzie
spiec rodziców i dzieci na pokładzie
opłata Taryfa zapłacona przez pasażera.
klasa Klasa pasażera na statku
pokład Który pasażer na pokładzie był
embark_town Z którego miasta wyruszył pasażer
sam Jeśli pasażer był sam

Przeglądaj dane

Najpierw przejrzyjmy niektóre dane i utwórzmy statystyki podsumowujące zestaw uczący.

 dftrain.head()
 
 dftrain.describe()
 

W zestawach szkoleniowych i ewaluacyjnych znajduje się odpowiednio 627 i 264 przykładów.

 dftrain.shape[0], dfeval.shape[0]
 
(627, 264)

Większość pasażerów ma 20 i 30 lat.

 dftrain.age.hist(bins=20)
plt.show()
 

png

Na pokładzie jest około dwa razy więcej pasażerów płci męskiej niż kobiety.

 dftrain.sex.value_counts().plot(kind='barh')
plt.show()
 

png

Większość pasażerów znajdowała się w „trzeciej” klasie.

 dftrain['class'].value_counts().plot(kind='barh')
plt.show()
 

png

Większość pasażerów wyruszyła z Southampton.

 dftrain['embark_town'].value_counts().plot(kind='barh')
plt.show()
 

png

Kobiety mają znacznie większe szanse na przeżycie niż mężczyźni. Będzie to niewątpliwie cecha predykcyjna modelu.

 pd.concat([dftrain, y_train], axis=1).groupby('sex').survived.mean().plot(kind='barh').set_xlabel('% survive')
plt.show()
 

png

Utwórz kolumny funkcji i funkcje wejściowe

Estymator Gradient Boosting może wykorzystywać zarówno cechy liczbowe, jak i jakościowe. Kolumny cech współpracują ze wszystkimi estymatorami TensorFlow, a ich celem jest zdefiniowanie cech używanych do modelowania. Ponadto zapewniają pewne funkcje inżynierskie, takie jak kodowanie na gorąco, normalizacja i grupowanie. W tym samouczku pola w kategorii CATEGORICAL_COLUMNS są przekształcane z kolumn kategorialnych na kolumny zakodowane na gorąco ( kolumna wskaźnika ):

 CATEGORICAL_COLUMNS = ['sex', 'n_siblings_spouses', 'parch', 'class', 'deck',
                       'embark_town', 'alone']
NUMERIC_COLUMNS = ['age', 'fare']

def one_hot_cat_column(feature_name, vocab):
  return tf.feature_column.indicator_column(
      tf.feature_column.categorical_column_with_vocabulary_list(feature_name,
                                                 vocab))
feature_columns = []
for feature_name in CATEGORICAL_COLUMNS:
  # Need to one-hot encode categorical features.
  vocabulary = dftrain[feature_name].unique()
  feature_columns.append(one_hot_cat_column(feature_name, vocabulary))

for feature_name in NUMERIC_COLUMNS:
  feature_columns.append(tf.feature_column.numeric_column(feature_name,
                                           dtype=tf.float32))
 

Możesz zobaczyć transformację, którą tworzy kolumna elementu. Na przykład, oto dane wyjściowe przy użyciu indicator_column w jednym przykładzie:

 example = dict(dftrain.head(1))
class_fc = tf.feature_column.indicator_column(tf.feature_column.categorical_column_with_vocabulary_list('class', ('First', 'Second', 'Third')))
print('Feature value: "{}"'.format(example['class'].iloc[0]))
print('One-hot encoded: ', tf.keras.layers.DenseFeatures([class_fc])(example).numpy())
 
Feature value: "Third"
One-hot encoded:  [[ 0.  0.  1.]]

Dodatkowo można wyświetlić wszystkie transformacje kolumn funkcji razem:

 tf.keras.layers.DenseFeatures(feature_columns)(example).numpy()
 
array([[ 22.  ,   1.  ,   0.  ,   1.  ,   0.  ,   0.  ,   1.  ,   0.  ,

          0.  ,   0.  ,   0.  ,   0.  ,   0.  ,   0.  ,   1.  ,   0.  ,
          0.  ,   0.  ,   7.25,   1.  ,   0.  ,   0.  ,   0.  ,   0.  ,
          0.  ,   0.  ,   1.  ,   0.  ,   0.  ,   0.  ,   0.  ,   0.  ,
          1.  ,   0.  ]], dtype=float32)

Następnie musisz utworzyć funkcje wejściowe. Określą one, w jaki sposób dane będą wczytywane do naszego modelu zarówno w celu uczenia, jak i wnioskowania. from_tensor_slices metody tf.data interfejsie API tf.data aby wczytać dane bezpośrednio z Pandas. Jest to odpowiednie dla mniejszych zestawów danych w pamięci. W przypadku większych zbiorów danych interfejs API tf.data obsługuje różne formaty plików (w tym csv ), dzięki czemu można przetwarzać zbiory danych, które nie mieszczą się w pamięci.

 # Use entire batch since this is such a small dataset.
NUM_EXAMPLES = len(y_train)

def make_input_fn(X, y, n_epochs=None, shuffle=True):
  def input_fn():
    dataset = tf.data.Dataset.from_tensor_slices((dict(X), y))
    if shuffle:
      dataset = dataset.shuffle(NUM_EXAMPLES)
    # For training, cycle thru dataset as many times as need (n_epochs=None).
    dataset = dataset.repeat(n_epochs)
    # In memory training doesn't use batching.
    dataset = dataset.batch(NUM_EXAMPLES)
    return dataset
  return input_fn

# Training and evaluation input functions.
train_input_fn = make_input_fn(dftrain, y_train)
eval_input_fn = make_input_fn(dfeval, y_eval, shuffle=False, n_epochs=1)
 

Trenuj i oceniaj model

Poniżej wykonasz następujące kroki:

  1. Zainicjuj model, określając cechy i hiperparametry.
  2. train_input_fn dane szkoleniowe do modelu przy użyciu parametru train_input_fn i train_input_fn model przy użyciu funkcji train .
  3. dfeval wydajność modelu przy użyciu zestawu ewaluacyjnego - w tym przykładzie dfeval DataFrame. Sprawdzisz, czy prognozy pasują do etykiet z tablicy y_eval .

Przed nauczeniem modelu drzew wzmocnionych, najpierw wytrenujmy klasyfikator liniowy (model regresji logistycznej). Najlepszą praktyką jest rozpoczęcie od prostszego modelu w celu ustalenia punktu odniesienia.

 linear_est = tf.estimator.LinearClassifier(feature_columns)

# Train model.
linear_est.train(train_input_fn, max_steps=100)

# Evaluation.
result = linear_est.evaluate(eval_input_fn)
clear_output()
print(pd.Series(result))
 
accuracy                  0.765152
accuracy_baseline         0.625000
auc                       0.832844
auc_precision_recall      0.789631
average_loss              0.478908
global_step             100.000000
label/mean                0.375000
loss                      0.478908
precision                 0.703297
prediction/mean           0.350790
recall                    0.646465
dtype: float64

Następnie wytrenujmy model Boosted Trees. W przypadku drzew wzmocnionych obsługiwana jest regresja ( BoostedTreesRegressor ) i klasyfikacja ( BoostedTreesClassifier ). Ponieważ celem jest przewidzenie klasy - BoostedTreesClassifier lub nie przeżyjesz, użyjesz BoostedTreesClassifier .

 # Since data fits into memory, use entire dataset per layer. It will be faster.
# Above one batch is defined as the entire dataset.
n_batches = 1
est = tf.estimator.BoostedTreesClassifier(feature_columns,
                                          n_batches_per_layer=n_batches)

# The model will stop training once the specified number of trees is built, not
# based on the number of steps.
est.train(train_input_fn, max_steps=100)

# Eval.
result = est.evaluate(eval_input_fn)
clear_output()
print(pd.Series(result))
 
accuracy                  0.829545
accuracy_baseline         0.625000
auc                       0.872788
auc_precision_recall      0.857807
average_loss              0.411839
global_step             100.000000
label/mean                0.375000
loss                      0.411839
precision                 0.793478
prediction/mean           0.381942
recall                    0.737374
dtype: float64

Teraz możesz użyć modelu pociągu do prognozowania pasażera na podstawie zestawu ocen. Modele TensorFlow są zoptymalizowane pod kątem tworzenia prognoz na podstawie partii lub kolekcji przykładów naraz. Wcześniej eval_input_fn jest definiowany przy użyciu całego zestawu wartościowania.

 pred_dicts = list(est.predict(eval_input_fn))
probs = pd.Series([pred['probabilities'][1] for pred in pred_dicts])

probs.plot(kind='hist', bins=20, title='predicted probabilities')
plt.show()
 

png

Na koniec możesz również przyjrzeć się charakterystyce operacyjnej odbiornika (ROC) wyników, co da nam lepsze wyobrażenie o kompromisie między współczynnikiem prawdziwie dodatnich i fałszywie dodatnich.

 from sklearn.metrics import roc_curve

fpr, tpr, _ = roc_curve(y_eval, probs)
plt.plot(fpr, tpr)
plt.title('ROC curve')
plt.xlabel('false positive rate')
plt.ylabel('true positive rate')
plt.xlim(0,)
plt.ylim(0,)
plt.show()
 

png