Maschinelles Lernen: Mischen von Ensemble in Python

Blending ist ein Ensemble-Algorithmus für maschinelles Lernen. Dies ist eine umgangssprachliche Bezeichnung für die gestapelte Verallgemeinerung [im Folgenden wird der in wissenschaftlichen Arbeiten akzeptierte Begriff „Verpackung“ anstelle des in wissenschaftlichen Arbeiten akzeptierten Begriffs „Stapelung“ verwendet] oder für das Verpackungsensemble, bei dem das Modell nicht auf Vorhersagen außerhalb der vom Basismodell gemachten Gruppen trainiert wird Vorhersagen für einen unabhängigen Datensatz.



Das Mischen wurde verwendet, um Stapelmodelle zu beschreiben, bei denen viele hundert Modelle im Rahmen des Netflix-Wettbewerbs für maschinelles Lernen im Wert von 1.000.000 US-Dollar zusammengefasst wurden. Daher ist das Mischen nach wie vor eine beliebte Methode und Bezeichnung für das Stapeln in Wettbewerben für maschinelles Lernen wie Kaggle ... Speziell für den Start eines neuen Streams des Kurses "Maschinelles Lernen"Wir teilen ein Tutorial darüber, wie man ein gemischtes Ensemble in Python entwickelt und bewertet. Nach Abschluss dieses Tutorials wissen Sie:



  • Gemischte Ensembles sind eine Art Modellverpackung, bei der das Metamodell unter Verwendung von Vorhersagen auf einem unabhängigen Testvalidierungsdatensatz anstelle von Vorhersagen während der k-fachen Kreuzvalidierung trainiert wird.
  • Wie man ein gemischtes Ensemble entwickelt, einschließlich Modelltraining und Vorhersagefunktionen basierend auf neuen Daten.
  • Bewertung gemischter Ensembles für Klassifizierungs- und prädiktive Regressionsmodellierungsprobleme.













Tutorial Übersicht



Dieses Tutorial ist in vier Teile gegliedert. Hier sind sie:



  • Gemischtes Ensemble.
  • Schaffung eines gemischten Ensembles.
  • Gemischtes Ensemble in einem Klassifikationsproblem.
  • Gemischtes Ensemble in einem Regressionsproblem.


Gemischtes Ensemble



Blending ist eine Ensemble-Technik für maschinelles Lernen, bei der mithilfe eines maschinellen Lernmodells gelernt wird, wie Vorhersagen aus mehreren Ensemblemitgliedermodellen am besten kombiniert werden können.



Das Mischen ist also dasselbe wie das als Stapeln bekannte Verallgemeinern des Stapelns. Mischen und Chargen werden häufig synonym in derselben Artikel- oder Modellbeschreibung verwendet.



Viele Praktiker des maschinellen Lernens haben Erfolg mit Batching und verwandten Techniken gefunden, um die Vorhersagegenauigkeit gegenüber jedem der einzelnen Modelle zu verbessern. In einigen Kontexten wird das Stapeln auch als Mischen bezeichnet. Wir werden hier auch Begriffe austauschen.

Feature-Weighted Linear Stacking , 2009.


Eine Stapelmodellarchitektur enthält zwei oder mehr Basismodelle, die häufig als Level-Zero-Modelle bezeichnet werden, und ein Metamodell, das die Vorhersagen des Basismodells als Level-One-Modell kombiniert. Das Metamodell wird basierend auf den Vorhersagen der Basismodelle für Daten außerhalb der Stichprobe trainiert.



  • Zero-Level- Modelle ( Basismodelle ) sind Modelle, die auf Trainingsdaten trainiert werden und deren Prognosen erfasst werden.
  • Das Modell der ersten Ebene ( Metamodell ) ist ein Modell, das lernt, die Prognosen der zugrunde liegenden Modelle am besten zu kombinieren.


Das Mischen hat jedoch bestimmte Konnotationen für den Aufbau eines verpackten Ensemblemodells. Das Mischen kann die Entwicklung eines Stapelensembles bieten, bei dem die Basismodelle jede Art von maschinellem Lernmodell sind, und das Metamodell ist ein lineares Modell, das die Vorhersagen der Basismodelle "mischt". Beispielsweise berechnet ein lineares Regressionsmodell bei der Vorhersage eines numerischen Werts oder ein logistisches Regressionsmodell bei der Vorhersage einer Klassenbezeichnung die gewichtete Summe der von den Basismodellen gemachten Vorhersagen und wird als Mischungsvorhersage behandelt.



  • Gemischtes Ensemble : Verwenden Sie ein lineares Modell wie lineare Regression oder logistische Regression als Metamodell in einem Batch-Modell-Ensemble.


Blending war ein Begriff, der während des Netflix-Wettbewerbs 2009 häufig für ein verpacktes Ensemble verwendet wurde. An dem Wettbewerb nahmen Teams teil, die nach Vorhersagemodellen suchten, die eine bessere Leistung als der native Netflix-Algorithmus erbrachten. Das Team erhielt einen Preis in Höhe von 1.000.000 US-Dollar, mit dem die Leistung um 10 Prozent verbessert wurde.



Unsere Lösung mit RMSE = 0,8643 ^ 2 ist eine lineare Mischung aus über 100 Ergebnissen. […] In der Beschreibung der Methoden werden die spezifischen Prädiktoren hervorgehoben, die an der endgültigen gemischten Lösung beteiligt waren.

Die BellKor 2008-Lösung für den Netflix-Preis 2008.


Mischen ist daher der umgangssprachliche Begriff für das Lernen von Ensembles mit einer Modellarchitektur wie Batching. Es wird selten, wenn überhaupt, in Lehrbüchern oder wissenschaftlichen Arbeiten verwendet, die sich nicht auf maschinelles Lernen im Wettbewerb beziehen. Am häufigsten wird der Begriff Mischung verwendet, um eine bestimmte Anwendung der Chargenbildung zu beschreiben, bei der ein Metamodell auf Vorhersagen trainiert wird, die von Basismodellen mit einem unabhängigen Validierungsdatensatz gemacht wurden. In diesem Zusammenhang ist die Verpackung dem Metamodell vorbehalten, das während des Kreuzvalidierungsverfahrens auf Vorhersagen trainiert wurde.



  • Mischen : Ein Ensemble vom Typ Batching, bei dem ein Metamodell auf Vorhersagen trainiert wird, die in einem unabhängigen Datensatz getroffen wurden.
  • Batching : Ein Batch-Ensemble, bei dem das Metamodell auf Vorhersagen trainiert wird, die während der k-fachen Kreuzvalidierung gemacht wurden.


Diese Unterscheidung ist in der Kaggle-Community für maschinelles Lernen üblich.



Mischen ist das Wort, das die Netflix-Gewinner geprägt haben. Es kommt der Verallgemeinerung sehr nahe, ist jedoch etwas einfacher und das Risiko von Informationslecks ist geringer. […] Durch Mischen erstellen Sie anstelle von Vorhersagen während der Kreuzvalidierung für den Trainingssatz einen kleinen unabhängigen Satz von beispielsweise 10% des Trainingssatzes. Das Chargenmodell wird dann nur an diesem kleinen Satz trainiert.

Kaggle Ensemble Guide , MLWave, 2015.


Wir verwenden die letzte Definition von Blending. Mal sehen, wie es umgesetzt wird.



Gemischte Ensembleentwicklung



Die Scikit-Learn-Bibliothek unterstützt zum Zeitpunkt des Schreibens kein sofortiges Mischen. Aber wir können es selbst mithilfe von Scikit-Lernmodellen implementieren. Zunächst müssen Sie eine Reihe von Basismodellen erstellen. Dies können beliebige Modelle sein, die wir für ein Regressions- oder Klassifizierungsproblem mögen. Wir können eine Funktion get_models () definieren , die eine Liste von Modellen zurückgibt, wobei jedes Modell als Tupel mit einem Namen und einem benutzerdefinierten Klassifikator oder Regressionsobjekt definiert ist. Für ein Klassifizierungsproblem könnten wir beispielsweise logistische Regression, kNN, Entscheidungsbaum, SVM und ein naives Bayes'sches Modell verwenden.



# get a list of base models
def get_models():
models = list()
models.append(('lr', LogisticRegression()))
models.append(('knn', KNeighborsClassifier()))
models.append(('cart', DecisionTreeClassifier()))
models.append(('svm', SVC(probability=True)))
models.append(('bayes', GaussianNB()))
return models
      
      





Als nächstes müssen wir das Mischmodell trainieren. Denken Sie daran, dass die Basismodelle im Trainingsdatensatz trainiert werden. Das Metamodell wird auf die Vorhersagen jedes Basismodells in einem unabhängigen Datensatz trainiert.



Zuerst können wir die Modelle in einer Liste durchlaufen und sie nacheinander im Trainingsdatensatz trainieren. Darüber hinaus können wir in diesem Zyklus ein trainiertes Modell verwenden, um eine Vorhersage für einen unabhängigen Datensatz (Validierung) zu treffen und Vorhersagen für die Zukunft zu speichern.



...
# fit all models on the training set and predict on hold out set
meta_X = list()
for name, model in models:
# fit in training set
model.fit(X_train, y_train)
# predict on hold out set
yhat = model.predict(X_val)
# reshape predictions into a matrix with one column
yhat = yhat.reshape(len(yhat), 1)
# store predictions as input for blending
meta_X.append(yhat)
      
      





Wir haben jetzt ein "meta_X *", das die Eingabe darstellt, die zum Trainieren des Metamodells verwendet werden kann. Jede Spalte oder jedes Objekt repräsentiert die Ausgabe eines Basismodells. Jede Zeile repräsentiert eine Stichprobe aus einem unabhängigen Datensatz. Mit der Funktion hstack () können wir sicherstellen, dass es sich bei diesem Datensatz um ein zweidimensionales Numpy-Array handelt, wie es vom Modell des maschinellen Lernens erwartet wird.



...
# create 2d array from predictions, each set is an input feature
meta_X = hstack(meta_X)
      
      





Wir können jetzt unser Metamodell trainieren. Es kann jedes beliebige maschinelle Lernmodell sein, das wir mögen, wie die logistische Regression für ein Klassifizierungsproblem.



...
# define blending model
blender = LogisticRegression()
# fit on predictions from base models
blender.fit(meta_X, y_val)
      
      





Sie können alles zu einer Funktion namens fit_ensemble () bündeln, die das Mischmodell mithilfe eines Trainings- und unabhängigen Validierungsdatensatzes trainiert.



# fit the blending ensemble
def fit_ensemble(models, X_train, X_val, y_train, y_val):
# fit all models on the training set and predict on hold out set
meta_X = list()
for name, model in models:
# fit in training set
model.fit(X_train, y_train)
# predict on hold out set
yhat = model.predict(X_val)
# reshape predictions into a matrix with one column
yhat = yhat.reshape(len(yhat), 1)
# store predictions as input for blending
meta_X.append(yhat)
# create 2d array from predictions, each set is an input feature
meta_X = hstack(meta_X)
# define blending model
blender = LogisticRegression()
# fit on predictions from base models
blender.fit(meta_X, y_val)
return blender
      
      





Der nächste Schritt besteht darin, ein Mischensemble zu verwenden, um neue Daten vorherzusagen. Dies ist ein zweistufiger Prozess. Der erste Schritt besteht darin, jedes Basismodell für die Prognose zu verwenden. Die Vorhersagen werden dann zusammengestellt und als Eingabe für das Mischungsmodell verwendet, um die endgültige Vorhersage zu treffen.



Wir können den gleichen Zyklus wie beim Training des Modells verwenden. Sammeln Sie also die Vorhersagen jedes Basismodells in einem Trainingsdatensatz, addieren Sie die Vorhersagen und rufen Sie Predict () für das Mischmodell mit diesem Metalevel-Datensatz auf. Predict_ensemble () Funktionunten implementiert diese Aktionen. Wenn Sie eine Liste mit Basismodellen, einen Ensemble-Mixer und einen Datensatz (z. B. einen Testdatensatz oder neue Daten) trainieren, werden für den Datensatz eine Reihe von Vorhersagen zurückgegeben.



# make a prediction with the blending ensemble
def predict_ensemble(models, blender, X_test):
# make predictions with base models
meta_X = list()
for name, model in models:
# predict with base model
yhat = model.predict(X_test)
# reshape predictions into a matrix with one column
yhat = yhat.reshape(len(yhat), 1)
# store prediction
meta_X.append(yhat)
# create 2d array from predictions, each set is an input feature
meta_X = hstack(meta_X)
# predict
return blender.predict(meta_X)
      
      





Wir haben jetzt alle Elemente, die erforderlich sind, um ein gemischtes Ensemble für Klassifizierungs- oder prädiktive Regressionsmodellierungsprobleme zu implementieren.



Gemischtes Ensemble für Klassifizierungsprobleme



In diesem Abschnitt werden wir uns mit der Verwendung von Blending für die Klassifizierungsaufgabe befassen. Erstens können wir die Funktion make_classification () verwenden , um ein synthetisches binäres Klassifizierungsproblem mit 10.000 Beispielen und 20 Eingabefunktionen zu erstellen. Das gesamte Beispiel ist unten dargestellt.



# test classification dataset
from sklearn.datasets import make_classification
# define dataset
X, y = make_classification(n_samples=10000, n_features=20, n_informative=15, n_redundant=5, random_state=7)
# summarize the dataset
print(X.shape, y.shape)
      
      





Durch Ausführen des Beispiels wird ein Datensatz erstellt und die Ein- und Ausgänge zusammengefasst.



(10000, 20) (10000,)
      
      





Als nächstes müssen wir den Datensatz zuerst in Trainings- und Testsätze aufteilen und dann den Trainingssatz in eine Teilmenge, die zum Trainieren der Grundmodelle verwendet wird, und eine Teilmenge, die zum Trainieren des Metamodells verwendet wird. In diesem Fall verwenden wir eine 50-50-Aufteilung für die Trainings- und Testsätze und dann eine 67-33-Aufteilung für die Trainings- und Validierungssätze.



...
# split dataset into train and test sets
X_train_full, X_test, y_train_full, y_test = train_test_split(X, y, test_size=0.5, random_state=1)
# split training set into train and validation sets
X_train, X_val, y_train, y_val = train_test_split(X_train_full, y_train_full, test_size=0.33, random_state=1)
# summarize data split
print('Train: %s, Val: %s, Test: %s' % (X_train.shape, X_val.shape, X_test.shape))
      
      





Sie können dann die Funktion get_models () aus dem vorherigen Abschnitt verwenden, um die im Ensemble verwendeten Klassifizierungsmodelle zu erstellen. Die Funktion fit_ensemble () kann dann aufgerufen werden, um das gemischte Ensemble für diese Datensätze zu trainieren, und die Funktion pred_ensemble () kann verwendet werden, um Vorhersagen für einen unabhängigen Datensatz zu treffen.



...
# create the base models
models = get_models()
# train the blending ensemble
blender = fit_ensemble(models, X_train, X_val, y_train, y_val)
# make predictions on test set
yhat = predict_ensemble(models, blender, X_test)
      
      





Schließlich können wir die Leistung des Mischungsmodells messen, indem wir die Klassifizierungsgenauigkeit im Testdatensatz angeben.



...
# evaluate predictions
score = accuracy_score(y_test, yhat)
print('Blending Accuracy: %.3f' % score)
      
      





Ein vollständiges Beispiel für die Schätzung eines gemischten Ensembles in einem synthetischen binären Klassifizierungsproblem ist unten angegeben.



# blending ensemble for classification using hard voting
from numpy import hstack
from sklearn.datasets import make_classification
from sklearn.model_selection import train_test_split
from sklearn.metrics import accuracy_score
from sklearn.linear_model import LogisticRegression
from sklearn.neighbors import KNeighborsClassifier
from sklearn.tree import DecisionTreeClassifier
from sklearn.svm import SVC
from sklearn.naive_bayes import GaussianNB

# get the dataset
def get_dataset():
X, y = make_classification(n_samples=10000, n_features=20, n_informative=15, n_redundant=5, random_state=7)
return X, y

# get a list of base models
def get_models():
models = list()
models.append(('lr', LogisticRegression()))
models.append(('knn', KNeighborsClassifier()))
models.append(('cart', DecisionTreeClassifier()))
models.append(('svm', SVC()))
models.append(('bayes', GaussianNB()))
return models

# fit the blending ensemble
def fit_ensemble(models, X_train, X_val, y_train, y_val):
# fit all models on the training set and predict on hold out set
meta_X = list()
for name, model in models:
# fit in training set
model.fit(X_train, y_train)
# predict on hold out set
yhat = model.predict(X_val)
# reshape predictions into a matrix with one column
yhat = yhat.reshape(len(yhat), 1)
# store predictions as input for blending
meta_X.append(yhat)
# create 2d array from predictions, each set is an input feature
meta_X = hstack(meta_X)
# define blending model
blender = LogisticRegression()
# fit on predictions from base models
blender.fit(meta_X, y_val)
return blender

# make a prediction with the blending ensemble
def predict_ensemble(models, blender, X_test):
# make predictions with base models
meta_X = list()
for name, model in models:
# predict with base model
yhat = model.predict(X_test)
# reshape predictions into a matrix with one column
yhat = yhat.reshape(len(yhat), 1)
# store prediction
meta_X.append(yhat)
# create 2d array from predictions, each set is an input feature
meta_X = hstack(meta_X)
# predict
return blender.predict(meta_X)

# define dataset
X, y = get_dataset()
# split dataset into train and test sets
X_train_full, X_test, y_train_full, y_test = train_test_split(X, y, test_size=0.5, random_state=1)
# split training set into train and validation sets
X_train, X_val, y_train, y_val = train_test_split(X_train_full, y_train_full, test_size=0.33, random_state=1)
# summarize data split
print('Train: %s, Val: %s, Test: %s' % (X_train.shape, X_val.shape, X_test.shape))
# create the base models
models = get_models()
# train the blending ensemble
blender = fit_ensemble(models, X_train, X_val, y_train, y_val)
# make predictions on test set
yhat = predict_ensemble(models, blender, X_test)
# evaluate predictions
score = accuracy_score(y_test, yhat)
print('Blending Accuracy: %.3f' % (score*100))
      
      





Wenn Sie das Beispiel ausführen, wird zuerst eine Zusammenfassung aller Datensätze und dann die Genauigkeit des Ensembles im Testdatensatz angezeigt.



Hinweis: Ihre Ergebnisse können aufgrund der stochastischen Natur des Algorithmus oder des Schätzverfahrens oder aufgrund von Unterschieden in der numerischen Genauigkeit variieren . Führen Sie das Beispiel mehrmals aus und vergleichen Sie das durchschnittliche Ergebnis.



Hier sehen wir, dass das gemischte Ensemble eine Klassifizierungsgenauigkeit von ca. 97.900% erreichte.



Train: (3350, 20), Val: (1650, 20), Test: (5000, 20)
Blending Accuracy: 97.900
      
      





Im vorherigen Beispiel wurde die Vorhersage klarer Klassenbezeichnungen unter Verwendung eines Mischmodells kombiniert. Dies ist eine Art harte Abstimmung . Eine Alternative ist eine Methode, bei der jedes Modell die Klassenwahrscheinlichkeiten vorhersagt und ein Metamodell verwendet, um die Wahrscheinlichkeiten zu mischen. Dies ist eine Art sanfte Abstimmung, die manchmal zu einer besseren Leistung führen kann. Zunächst müssen wir Modelle konfigurieren, die Wahrscheinlichkeiten zurückgeben, z. B. das SVM-Modell.



# get a list of base models
def get_models():
models = list()
models.append(('lr', LogisticRegression()))
models.append(('knn', KNeighborsClassifier()))
models.append(('cart', DecisionTreeClassifier()))
models.append(('svm', SVC(probability=True)))
models.append(('bayes', GaussianNB()))
return models
      
      





Dann müssen die zugrunde liegenden Modelle geändert werden, um Wahrscheinlichkeiten anstelle klarer Klassenbezeichnungen vorherzusagen. Dies kann erreicht werden, indem Predict_proba () in fit_ensemble () aufgerufen wird, während die zugrunde liegenden Modelle trainiert werden.



...
# fit all models on the training set and predict on hold out set
meta_X = list()
for name, model in models:
# fit in training set
model.fit(X_train, y_train)
# predict on hold out set
yhat = model.predict_proba(X_val)
# store predictions as input for blending
meta_X.append(yhat)
      
      





Dies bedeutet, dass der zum Trainieren des Metamodells verwendete Metadatensatz n Spalten pro Klassifizierer enthält, wobei n die Anzahl der Klassen im Prognoseproblem ist. In unserem Fall gibt es zwei Klassen. Wir müssen auch die Vorhersagen der Basismodelle ändern, wenn wir das Mischmodell verwenden, um neue Daten vorherzusagen.



...
# make predictions with base models
meta_X = list()
for name, model in models:
# predict with base model
yhat = model.predict_proba(X_test)
# store prediction
meta_X.append(yhat)
      
      





Das gesamte Beispiel für die Verwendung des Mischens auf vorhergesagten Klassenwahrscheinlichkeiten für ein synthetisches binäres Klassifizierungsproblem ist unten angegeben.




# blending ensemble for classification using soft voting
from numpy import hstack
from sklearn.datasets import make_classification
from sklearn.model_selection import train_test_split
from sklearn.metrics import accuracy_score
from sklearn.linear_model import LogisticRegression
from sklearn.neighbors import KNeighborsClassifier
from sklearn.tree import DecisionTreeClassifier
from sklearn.svm import SVC
from sklearn.naive_bayes import GaussianNB

# get the dataset
def get_dataset():
X, y = make_classification(n_samples=10000, n_features=20, n_informative=15, n_redundant=5, random_state=7)
return X, y

# get a list of base models
def get_models():
models = list()
models.append(('lr', LogisticRegression()))
models.append(('knn', KNeighborsClassifier()))
models.append(('cart', DecisionTreeClassifier()))
models.append(('svm', SVC(probability=True)))
models.append(('bayes', GaussianNB()))
return models

# fit the blending ensemble
def fit_ensemble(models, X_train, X_val, y_train, y_val):
# fit all models on the training set and predict on hold out set
meta_X = list()
for name, model in models:
# fit in training set
model.fit(X_train, y_train)
# predict on hold out set
yhat = model.predict_proba(X_val)
# store predictions as input for blending
meta_X.append(yhat)
# create 2d array from predictions, each set is an input feature
meta_X = hstack(meta_X)
# define blending model
blender = LogisticRegression()
# fit on predictions from base models
blender.fit(meta_X, y_val)
return blender

# make a prediction with the blending ensemble
def predict_ensemble(models, blender, X_test):
# make predictions with base models
meta_X = list()
for name, model in models:
# predict with base model
yhat = model.predict_proba(X_test)
# store prediction
meta_X.append(yhat)
# create 2d array from predictions, each set is an input feature
meta_X = hstack(meta_X)
# predict
return blender.predict(meta_X)

# define dataset
X, y = get_dataset()
# split dataset into train and test sets
X_train_full, X_test, y_train_full, y_test = train_test_split(X, y, test_size=0.5, random_state=1)
# split training set into train and validation sets
X_train, X_val, y_train, y_val = train_test_split(X_train_full, y_train_full, test_size=0.33, random_state=1)
# summarize data split
print('Train: %s, Val: %s, Test: %s' % (X_train.shape, X_val.shape, X_test.shape))
# create the base models
models = get_models()
# train the blending ensemble
blender = fit_ensemble(models, X_train, X_val, y_train, y_val)
# make predictions on test set
yhat = predict_ensemble(models, blender, X_test)
# evaluate predictions
score = accuracy_score(y_test, yhat)
print('Blending Accuracy: %.3f' % (score*100))
      
      





Wenn Sie das Beispiel ausführen, wird zuerst eine Zusammenfassung aller Datensätze und dann die Genauigkeit des Ensembles im Testsatz angezeigt.



Hinweis: Ihre Ergebnisse können aufgrund der stochastischen Natur des Algorithmus oder des Schätzverfahrens oder aufgrund von Unterschieden in der numerischen Genauigkeit variieren . Probieren Sie das Beispiel mehrmals aus und vergleichen Sie das durchschnittliche Ergebnis.



Hier sehen wir, dass die Vermischung der Klassenwahrscheinlichkeiten zu einer Erhöhung der Klassifizierungsgenauigkeit auf etwa 98,240% führte.



Train: (3350, 20), Val: (1650, 20), Test: (5000, 20)
Blending Accuracy: 98.240
      
      





Ein gemischtes Ensemble ist nur dann effektiv, wenn es in der Lage ist, eines der einzelnen Modelle zu übertreffen. Wir können dies bestätigen, indem wir jedes der Basismodelle separat bewerten. Jedes Basismodell kann auf dem gesamten Trainingsdatensatz (im Gegensatz zu einem Mischensemble) trainiert und auf dem Testdatensatz (genau wie in einem Mischensemble) ausgewertet werden. Das folgende Beispiel zeigt dies, indem jedes Basismodell separat bewertet wird.



# evaluate base models on the entire training dataset
from sklearn.datasets import make_classification
from sklearn.model_selection import train_test_split
from sklearn.metrics import accuracy_score
from sklearn.linear_model import LogisticRegression
from sklearn.neighbors import KNeighborsClassifier
from sklearn.tree import DecisionTreeClassifier
from sklearn.svm import SVC
from sklearn.naive_bayes import GaussianNB

# get the dataset
def get_dataset():
X, y = make_classification(n_samples=10000, n_features=20, n_informative=15, n_redundant=5, random_state=7)
return X, y

# get a list of base models
def get_models():
models = list()
models.append(('lr', LogisticRegression()))
models.append(('knn', KNeighborsClassifier()))
models.append(('cart', DecisionTreeClassifier()))
models.append(('svm', SVC(probability=True)))
models.append(('bayes', GaussianNB()))
return models

# define dataset
X, y = get_dataset()
# split dataset into train and test sets
X_train_full, X_test, y_train_full, y_test = train_test_split(X, y, test_size=0.5, random_state=1)
# summarize data split
print('Train: %s, Test: %s' % (X_train_full.shape, X_test.shape))
# create the base models
models = get_models()
# evaluate standalone model
for name, model in models:
# fit the model on the training dataset
model.fit(X_train_full, y_train_full)
# make a prediction on the test dataset
yhat = model.predict(X_test)
# evaluate the predictions
score = accuracy_score(y_test, yhat)
# report the score
print('>%s Accuracy: %.3f' % (name, score*100))
      
      







Wenn Sie das Beispiel ausführen, wird zuerst eine Zusammenfassung aller drei Datensätze und dann die Genauigkeit jedes Basismodells im Testsatz angezeigt.



Hinweis: Ihre Ergebnisse können aufgrund der stochastischen Natur des Algorithmus oder des Schätzverfahrens oder aufgrund von Unterschieden in der numerischen Genauigkeit abweichen. Probieren Sie das Beispiel mehrmals aus und vergleichen Sie das durchschnittliche Ergebnis.



In diesem Fall sehen wir, dass alle Modelle schlechter abschneiden als ein gemischtes Ensemble. Das Interessante ist, dass wir sehen können, dass die SVM der Genauigkeit von 98.200% sehr nahe kommt, verglichen mit der Genauigkeit von 98.240%, die mit dem gemischten Ensemble erreicht wird.



Train: (5000, 20), Test: (5000, 20)
>lr Accuracy: 87.800
>knn Accuracy: 97.380
>cart Accuracy: 88.200
>svm Accuracy: 98.200
>bayes Accuracy: 87.300
      
      





Wir können ein gemischtes Ensemble als unser endgültiges Modell wählen. Dies beinhaltet das Trainieren des Ensembles für den gesamten Trainingsdatensatz und das Erstellen von Vorhersagen anhand neuer Beispiele. Insbesondere wird der gesamte Trainingssatz in Trainings- und Validierungssätze zum Trainieren des Basis- bzw. Metamodells unterteilt, und dann kann das Ensemble für die Vorhersage verwendet werden. Ein vollständiges Beispiel für die Vorhersage neuer Daten unter Verwendung eines gemischten Ensembles zur Klassifizierung sieht folgendermaßen aus:



# example of making a prediction with a blending ensemble for classification
from numpy import hstack
from sklearn.datasets import make_classification
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LogisticRegression
from sklearn.neighbors import KNeighborsClassifier
from sklearn.tree import DecisionTreeClassifier
from sklearn.svm import SVC
from sklearn.naive_bayes import GaussianNB

# get the dataset
def get_dataset():
X, y = make_classification(n_samples=10000, n_features=20, n_informative=15, n_redundant=5, random_state=7)
return X, y

# get a list of base models
def get_models():
models = list()
models.append(('lr', LogisticRegression()))
models.append(('knn', KNeighborsClassifier()))
models.append(('cart', DecisionTreeClassifier()))
models.append(('svm', SVC(probability=True)))
models.append(('bayes', GaussianNB()))
return models

# fit the blending ensemble
def fit_ensemble(models, X_train, X_val, y_train, y_val):
# fit all models on the training set and predict on hold out set
meta_X = list()
for _, model in models:
# fit in training set
model.fit(X_train, y_train)
# predict on hold out set
yhat = model.predict_proba(X_val)
# store predictions as input for blending
meta_X.append(yhat)
# create 2d array from predictions, each set is an input feature
meta_X = hstack(meta_X)
# define blending model
blender = LogisticRegression()
# fit on predictions from base models
blender.fit(meta_X, y_val)
return blender

# make a prediction with the blending ensemble
def predict_ensemble(models, blender, X_test):
# make predictions with base models
meta_X = list()
for _, model in models:
# predict with base model
yhat = model.predict_proba(X_test)
# store prediction
meta_X.append(yhat)
# create 2d array from predictions, each set is an input feature
meta_X = hstack(meta_X)
# predict
return blender.predict(meta_X)

# define dataset
X, y = get_dataset()
# split dataset set into train and validation sets
X_train, X_val, y_train, y_val = train_test_split(X, y, test_size=0.33, random_state=1)
# summarize data split
print('Train: %s, Val: %s' % (X_train.shape, X_val.shape))
# create the base models
models = get_models()
# train the blending ensemble
blender = fit_ensemble(models, X_train, X_val, y_train, y_val)
# make a prediction on a new row of data
row = [-0.30335011, 2.68066314, 2.07794281, 1.15253537, -2.0583897, -2.51936601, 0.67513028, -3.20651939, -1.60345385, 3.68820714, 0.05370913, 1.35804433, 0.42011397, 1.4732839, 2.89997622, 1.61119399, 7.72630965, -2.84089477, -1.83977415, 1.34381989]
yhat = predict_ensemble(models, blender, [row])
# summarize prediction
print('Predicted Class: %d' % (yhat))
      
      





Durch Ausführen des Beispiels wird ein gemischtes Ensemble-Modell für ein Dataset trainiert und anschließend eine neue Datenzeile vorhergesagt, wie dies bei Verwendung des Modells in einer Anwendung der Fall wäre.



Train: (6700, 20), Val: (3300, 20)
Predicted Class: 1
      
      





Mal sehen, wie wir das gemischte Ensemble auf Regression bewerten können.



Gemischtes Ensemble für Regressionsprobleme



In diesem Abschnitt werden wir uns mit der Verwendung der Stapelverarbeitung für ein Regressionsproblem befassen. Erstens können wir die Funktion make_regression () verwenden , um ein synthetisches Regressionsproblem mit 10.000 Stichproben und 20 Eingabefunktionen zu erstellen. Das gesamte Beispiel ist unten dargestellt.



# test regression dataset
from sklearn.datasets import make_regression
# define dataset
X, y = make_regression(n_samples=10000, n_features=20, n_informative=10, noise=0.3, random_state=7)
# summarize the dataset
print(X.shape, y.shape)
      
      





Durch Ausführen des Beispiels wird ein Dataset erstellt und die Eingabe- und Ausgabekomponenten zusammengefasst.



(10000, 20) (10000,)
      
      





Als Nächstes können Sie eine Liste von Regressionsmodellen definieren, die als Basis verwendet werden sollen. In diesem Fall verwenden wir lineare Regressions-, kNN-, Entscheidungsbaum- und SVM-Modelle.



# get a list of base models
def get_models():
models = list()
models.append(('lr', LinearRegression()))
models.append(('knn', KNeighborsRegressor()))
models.append(('cart', DecisionTreeRegressor()))
models.append(('svm', SVR()))
return models
      
      





Die zum Trainieren des Ensembles verwendete Funktion fit_ensemble () ändert sich nicht, außer dass das zum Mischen verwendete Modell in Regression geändert werden muss. Hier verwenden wir ein lineares Regressionsmodell.



...
# define blending model
blender = LinearRegression()
      
      





Da dies ein Regressionsproblem ist, bewerten wir die Leistung des Modells anhand der Fehlermetrik, in diesem Fall des durchschnittlichen absoluten Fehlers oder (abgekürzt) MAE.



...
# evaluate predictions
score = mean_absolute_error(y_test, yhat)
print('Blending MAE: %.3f' % score)
      
      





Das gesamte Beispiel eines gemischten Ensembles für ein Problem der prädiktiven Modellierung der synthetischen Regression ist unten dargestellt:



# evaluate blending ensemble for regression
from numpy import hstack
from sklearn.datasets import make_regression
from sklearn.model_selection import train_test_split
from sklearn.metrics import mean_absolute_error
from sklearn.linear_model import LinearRegression
from sklearn.neighbors import KNeighborsRegressor
from sklearn.tree import DecisionTreeRegressor
from sklearn.svm import SVR

# get the dataset
def get_dataset():
X, y = make_regression(n_samples=10000, n_features=20, n_informative=10, noise=0.3, random_state=7)
return X, y

# get a list of base models
def get_models():
models = list()
models.append(('lr', LinearRegression()))
models.append(('knn', KNeighborsRegressor()))
models.append(('cart', DecisionTreeRegressor()))
models.append(('svm', SVR()))
return models

# fit the blending ensemble
def fit_ensemble(models, X_train, X_val, y_train, y_val):
# fit all models on the training set and predict on hold out set
meta_X = list()
for name, model in models:
# fit in training set
model.fit(X_train, y_train)
# predict on hold out set
yhat = model.predict(X_val)
# reshape predictions into a matrix with one column
yhat = yhat.reshape(len(yhat), 1)
# store predictions as input for blending
meta_X.append(yhat)
# create 2d array from predictions, each set is an input feature
meta_X = hstack(meta_X)
# define blending model
blender = LinearRegression()
# fit on predictions from base models
blender.fit(meta_X, y_val)
return blender

# make a prediction with the blending ensemble
def predict_ensemble(models, blender, X_test):
# make predictions with base models
meta_X = list()
for name, model in models:
# predict with base model
yhat = model.predict(X_test)
# reshape predictions into a matrix with one column
yhat = yhat.reshape(len(yhat), 1)
# store prediction
meta_X.append(yhat)
# create 2d array from predictions, each set is an input feature
meta_X = hstack(meta_X)
# predict
return blender.predict(meta_X)

# define dataset
X, y = get_dataset()
# split dataset into train and test sets
X_train_full, X_test, y_train_full, y_test = train_test_split(X, y, test_size=0.5, random_state=1)
# split training set into train and validation sets
X_train, X_val, y_train, y_val = train_test_split(X_train_full, y_train_full, test_size=0.33, random_state=1)
# summarize data split
print('Train: %s, Val: %s, Test: %s' % (X_train.shape, X_val.shape, X_test.shape))
# create the base models
models = get_models()
# train the blending ensemble
blender = fit_ensemble(models, X_train, X_val, y_train, y_val)
# make predictions on test set
yhat = predict_ensemble(models, blender, X_test)
# evaluate predictions
score = mean_absolute_error(y_test, yhat)
print('Blending MAE: %.3f' % score)
      
      





Das Beispiel druckt zuerst eine Zusammenfassung der drei Datensätze und dann die MAE auf dem Testsatz.



Hinweis: Ihre Ergebnisse können aufgrund der stochastischen Natur des Algorithmus oder des Schätzverfahrens oder aufgrund von Unterschieden in der numerischen Genauigkeit variieren . Probieren Sie das Beispiel mehrmals aus und vergleichen Sie das durchschnittliche Ergebnis.



Hier sehen wir, dass das Ensemble im Testdatensatz einen MAE von etwa 0,237 erreichte.



Train: (3350, 20), Val: (1650, 20), Test: (5000, 20)
Blending MAE: 0.237
      
      





Wie bei der Klassifizierung ist ein gemischtes Ensemble nur dann nützlich, wenn es eine bessere Leistung als eines der grundlegenden Ensemble-Modelle erbringt.



Wir können dies testen, indem wir jedes Basismodell isoliert bewerten, es zuerst auf dem gesamten Trainingssatz (im Gegensatz zu einem Ensemble) trainieren und Vorhersagen auf dem Testdatensatz (wie in einem Ensemble) treffen. Im folgenden Beispiel wird jedes der Basismodelle isoliert anhand eines synthetischen Datensatzes zur prädiktiven Regressionsmodellierung geschätzt.



# evaluate base models in isolation on the regression dataset
from numpy import hstack
from sklearn.datasets import make_regression
from sklearn.model_selection import train_test_split
from sklearn.metrics import mean_absolute_error
from sklearn.linear_model import LinearRegression
from sklearn.neighbors import KNeighborsRegressor
from sklearn.tree import DecisionTreeRegressor
from sklearn.svm import SVR

# get the dataset
def get_dataset():
X, y = make_regression(n_samples=10000, n_features=20, n_informative=10, noise=0.3, random_state=7)
return X, y

# get a list of base models
def get_models():
models = list()
models.append(('lr', LinearRegression()))
models.append(('knn', KNeighborsRegressor()))
models.append(('cart', DecisionTreeRegressor()))
models.append(('svm', SVR()))
return models

# define dataset
X, y = get_dataset()
# split dataset into train and test sets
X_train_full, X_test, y_train_full, y_test = train_test_split(X, y, test_size=0.5, random_state=1)
# summarize data split
print('Train: %s, Test: %s' % (X_train_full.shape, X_test.shape))
# create the base models
models = get_models()
# evaluate standalone model
for name, model in models:
# fit the model on the training dataset
model.fit(X_train_full, y_train_full)
# make a prediction on the test dataset
yhat = model.predict(X_test)
# evaluate the predictions
score = mean_absolute_error(y_test, yhat)
# report the score
print('>%s MAE: %.3f' % (name, score))
      
      





Wenn Sie das Beispiel ausführen, werden zuerst die Trainings- und Testsätze und dann die MAE jedes Basismodells im Testdatensatz zusammengefasst.



Hinweis: Ihre Ergebnisse können aufgrund der stochastischen Natur des Algorithmus oder des Schätzverfahrens oder aufgrund von Unterschieden in der numerischen Genauigkeit variieren . Probieren Sie das Beispiel mehrmals aus und vergleichen Sie das durchschnittliche Ergebnis.



Hier können Sie sehen, dass das lineare Regressionsmodell tatsächlich etwas besser abschnitt als das gemischte Ensemble und einen MAE von 0,236 im Vergleich zu 0,237 erreichte. Dies hängt möglicherweise damit zusammen, wie der synthetische Datensatz erstellt wurde.



In diesem Fall würden wir es jedoch vorziehen, für genau diese Aufgabe ein lineares Regressionsmodell zu verwenden. Diese Situation unterstreicht, wie wichtig es ist, die Leistung der beitragenden Modelle zu validieren, bevor das Ensemblemodell als endgültig akzeptiert wird.



Train: (5000, 20), Test: (5000, 20)
>lr MAE: 0.236
>knn MAE: 100.169
>cart MAE: 133.744
>svm MAE: 138.195
      
      





Auch hier können Sie das gemischte Ensemble als endgültiges Regressionsmodell anwenden. Der Ansatz besteht darin, den gesamten Datensatz in Trainings- und Testsätze aufzuteilen, um die Basislinie und die Metamodelle darauf zu trainieren. Anschließend kann das Ensemble verwendet werden, um eine neue Datenzeile vorherzusagen. Ein vollständiges Beispiel für die Erstellung einer Prognose aus neuen Daten unter Verwendung eines gemischten Ensembles für ein Regressionsproblem ist unten angegeben.



# example of making a prediction with a blending ensemble for regression
from numpy import hstack
from sklearn.datasets import make_regression
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LinearRegression
from sklearn.neighbors import KNeighborsRegressor
from sklearn.tree import DecisionTreeRegressor
from sklearn.svm import SVR

# get the dataset
def get_dataset():
X, y = make_regression(n_samples=10000, n_features=20, n_informative=10, noise=0.3, random_state=7)
return X, y

# get a list of base models
def get_models():
models = list()
models.append(('lr', LinearRegression()))
models.append(('knn', KNeighborsRegressor()))
models.append(('cart', DecisionTreeRegressor()))
models.append(('svm', SVR()))
return models

# fit the blending ensemble
def fit_ensemble(models, X_train, X_val, y_train, y_val):
# fit all models on the training set and predict on hold out set
meta_X = list()
for _, model in models:
# fit in training set
model.fit(X_train, y_train)
# predict on hold out set
yhat = model.predict(X_val)
# reshape predictions into a matrix with one column
yhat = yhat.reshape(len(yhat), 1)
# store predictions as input for blending
meta_X.append(yhat)
# create 2d array from predictions, each set is an input feature
meta_X = hstack(meta_X)
# define blending model
blender = LinearRegression()
# fit on predictions from base models
blender.fit(meta_X, y_val)
return blender

# make a prediction with the blending ensemble
def predict_ensemble(models, blender, X_test):
# make predictions with base models
meta_X = list()
for _, model in models:
# predict with base model
yhat = model.predict(X_test)
# reshape predictions into a matrix with one column
yhat = yhat.reshape(len(yhat), 1)
# store prediction
meta_X.append(yhat)
# create 2d array from predictions, each set is an input feature
meta_X = hstack(meta_X)
# predict
return blender.predict(meta_X)

# define dataset
X, y = get_dataset()
# split dataset set into train and validation sets
X_train, X_val, y_train, y_val = train_test_split(X, y, test_size=0.33, random_state=1)
# summarize data split
print('Train: %s, Val: %s' % (X_train.shape, X_val.shape))
# create the base models
models = get_models()
# train the blending ensemble
blender = fit_ensemble(models, X_train, X_val, y_train, y_val)
# make a prediction on a new row of data
row = [-0.24038754, 0.55423865, -0.48979221, 1.56074459, -1.16007611, 1.10049103, 1.18385406, -1.57344162, 0.97862519, -0.03166643, 1.77099821, 1.98645499, 0.86780193, 2.01534177, 2.51509494, -1.04609004, -0.19428148, -0.05967386, -2.67168985, 1.07182911]
yhat = predict_ensemble(models, blender, [row])
# summarize prediction
print('Predicted: %.3f' % (yhat[0]))
      
      





Durch Ausführen des Beispiels wird ein Ensemble-Modell für ein Dataset trainiert und anschließend eine neue Datenzeile vorhergesagt, wie dies bei Verwendung des Modells in einer Anwendung der Fall wäre.



Train: (6700, 20), Val: (3300, 20)
Predicted: 359.986
      
      





Dieser Abschnitt enthält Ressourcen zu diesem Thema, wenn Sie tiefer in dieses Thema eintauchen möchten.














Und vergessen Sie nicht den Promo-Code HABR , der den Banner-Rabatt um 10% erhöht .



Bild








Weitere Kurse


empfohlene Artikel






All Articles