(In Bezug auf den Benchmark-Test [Addition](http://qiita.com/TomokIshii/items/b5708a02895847e3588c#%E8%BF%BD%E8%A8%98-theano-gpu%E8%A8%88%E7%AE% 97% E3% 81% A7mini-Charge% E3% 82% B5% E3% 82% A4% E3% 82% BA% E3% 81% AB% E7% 9D% 80% E7% 9B% AE% E3% 81% 97% E3% 81% A6% E3% 83% 99% E3% 83% B3% E3% 83% 81% E3% 83% 9E% E3% 83% BC% E3% 82% AF).
Neulich habe ich in Qiita darüber geschrieben, wie man die Programmieraufgabe (Matlab) des Coursera-Kurses für maschinelles Lernen (von der Stanford University, Prof. Andrew Ng) genießt, während ich ihn auf Python portiere. Danach habe ich den Kurs besucht, aber ich habe gelernt, dass es keine Programmieraufgaben gibt, auf die ich mich seit Woche 10 gefreut habe. (Von den insgesamt 11 Wochen ist die Programmzuweisung von Woche 1 bis Woche 9 verfügbar. Quiz ist übrigens auch Woche 10 und 11.)
Woche 10 war interessant für Vorlesungen über stochastischen Gradientenabstieg (SGD) und Online-Lernen, da es als "maschinelles Lernen im großen Maßstab" bezeichnet wurde. Wenn es jedoch keine Programmieraufgaben gibt, werde ich selbst lernen. Deshalb haben wir SGD von Python implementiert. (Dies ist ein Versuch, das Deep Learning Framework "Theano" zusammen mit der Implementierung von SGD zu untersuchen.) Außerdem werde ich einige interessante Ergebnisse (Tipps) in den Benchmark-Test einführen, der nach der Implementierung von SGD durchgeführt wurde. ..
Das Video erklärt den stochastischen Gradientenabstieg im Gegensatz zum normalen Batch-Gradientenabstieg.
Batch Gradient Descent Kostenfunktion:
J_{train}(\theta) = \frac{1}{2m} \sum_{i=1}^{m} (h_{\theta} (x^{(i)})
- y^{(i)} ) ^2
Die folgende iterative Berechnung wird durchgeführt, um diese Kostenfunktion zu minimieren. Repeat {
{\theta}_j := {\theta}_j - \alpha \frac{1}{m} \sum_{i=1}^{m}(h_{\theta} (x^{(i)}
-y^{(i)} ) x_j^{(i)}
\\ \ \ \ \ \ \ \ \ \ (\textbf{for every } j=0, ..., n)
}
Stochastic Gradient Descent 1. Randomly shuffle (reorder) training examples Mischen Sie die Trainingsdaten nach dem Zufallsprinzip.
** 2. ** Aktualisieren Sie unten $ \ theta $, indem Sie nacheinander auf die Trainingsdaten verweisen. Repeat {
for\ i:= 1,...,m {\ \ \ \ \ \ \{\\
{\theta}_j := {\theta}_j - \alpha (h_{\theta} (x^{(i)}) - y^{(i)}) x_j^{(i)}
\\\ \ \ (\textbf{for every } j=0, ...,n)
\\\ \ \ \}
\ \ }
}
In der Vorlesung erklärte ich, wie man die Parameter aktualisiert, indem man sich nacheinander auf die Trainingsdaten bezieht, und dann gab es einen Mini-Batch-Gradientenabstieg (als Methode zwischen Batch-Gradientenabstieg und stochastischer GD). Es war.
Für die Daten, die zum Überprüfen des Codes verwendet wurden, habe ich den Datensatz "Adult" aus dem UCI Machine Learning Repository ausgewählt. Dies wird aus der US-Volkszählungsdatenbank extrahiert und scheint beliebte Daten beim maschinellen Lernen zu sein.
39, State-gov, 77516, Bachelors, 13, Never-married, Adm-clerical, Not-in-family, White, Male, 2174, 0, 40, United-States, <=50K
50, Self-emp-not-inc, 83311, Bachelors, 13, Married-civ-spouse, Exec-managerial, Husband, White, Male, 0, 0, 13, United-States, <=50K
38, Private, 215646, HS-grad, 9, Divorced, Handlers-cleaners, Not-in-family, White, Male, 0, 0, 40, United-States, <=50K
53, Private, 234721, 11th, 7, Married-civ-spouse, Handlers-cleaners, Husband, Black, Male, 0, 0, 40, United-States, <=50K
28, Private, 338409, Bachelors, 13, Married-civ-spouse, Prof-specialty, Wife, Black, Female, 0, 0, 40, Cuba, <=50K
Alter, akademischer Hintergrund, Berufstyp, Heiratsgeschichte usw. sind in einer Reihe, aber am Ende jeder Zeile steht die Bezeichnung der Einkommensklasse "<= 50.000" oder "> 50.000". Dies ist die erläuterte Variable, die für die Klassifizierung verwendet wird. Ich bin verwirrt darüber, was ich als erklärende Variable (Funktion) für die Regression auswählen soll, aber diesmal habe ich nur ein Jahr Einschulung gewählt. Es wird angenommen, dass der akademische Hintergrund eine etwas höhere Auflösung hat, aber es scheint, dass dies mit dem Einkommen in der Welt zusammenhängt.
Wir beginnen mit der Definition einer Kostenfunktion und einer Funktion zur Berechnung ihres Gradienten nach der Methode der vorherigen Aufgaben von Coursera Machine Learning.
import numpy as np
import pandas as pd
import timeit
import theano
import theano.tensor as T
def load_data():
(Weggelassen)
return xtr, ytr, xte, yte
def compute_cost(w, b, x, y):
p_1 = 1 / (1 + T.exp(-T.dot(x, w) -b)) # same as sigmoid(T.dot(x,w)+b)
income_class = lambda predictor: T.gt(predictor, 0.5) # 0.5 is threshold
prediction = income_class(p_1)
xent = -y * T.log(p_1) - (1-y) * T.log(1- p_1)
cost = xent.mean() + 0.01 * (w ** 2).sum() # regularization
return cost, prediction
def compute_grad(cost, w, b):
gw, gb = T.grad(cost, [w, b])
return gw, gb
Ein Merkmal des Frameworks "Theano" ist, dass Sie, sobald Sie sich daran gewöhnt haben (es ist schwer zu verstehen, wenn Sie nicht daran gewöhnt sind), eine Aussage sehr präzise zusammenstellen können. (Insbesondere kann die Berechnung des Gradienten in einer Zeile erfolgen.)
Die Hauptverarbeitung wird mit diesen Funktionen durchgeführt.
xtr, ytr, xte, yte = load_data()
# Declare Theano symbolic variables
xtr_shape = xtr.shape
if len(xtr_shape) == 2:
w_len = xtr_shape[1]
else:
w_len = 1
x = T.matrix('x') # for xmat
y = T.vector('y') # for ymat, labels
w = theano.shared(np.zeros(w_len), name='w') # w, b <- all zero
b = theano.shared(0., name='b')
print ' Initial model: '
wi = w.get_value()
bi = w.get_value()
print 'w : [%12.4f], b : [%12.4f]' % (wi[0], bi)
cost, prediction = compute_cost(w, b, x, y) # ... Cost-J
gw, gb = compute_grad(cost, w, b) # ... Gradients
# Compile
train = theano.function(
inputs=[x,y],
outputs=[cost, prediction],
updates=((w, w - 0.1 * gw), (b, b - 0.1 * gb)),
allow_input_downcast=True)
predict = theano.function(inputs=[x], outputs=prediction,
allow_input_downcast=True)
# Train (Optimization)
start_time = timeit.default_timer()
training_steps = 10000
xtr= xtr.reshape(len(xtr), 1) # shape: (m,) to (m,1)
for i in range(training_steps):
cost_j, pred = train(xtr, ytr)
Wie oben beschrieben, wurden die Parameter (w, b), die die Kostenfunktion minimieren, durch das Gradientenabstiegsverfahren (Batch-Gradientenabstieg) erhalten. Eine Konvergenzbeurteilung wird nicht durchgeführt, und die Lösung wird erhalten, indem die Parameter eine vorbestimmte Anzahl von Malen aktualisiert werden.
Dies ist nun die Implementierung des Hauptthemas Stochastic Gradient Descent (probabilistische Gradient Descent-Methode). In Couseras Vortrag gab es eine Erklärung für den stochastischen Gradientenabstieg, bei dem Daten gescannt werden, die zum Lernen eines Satzes nach dem anderen verwendet werden, und für den stochastischen Mini-Batch-Gradientenabstieg, bei dem Daten von 2 bis 100 Sätzen kleiner Größe nacheinander gescannt werden. Wählen Sie die Mini-Charge.
In SGD werden Trainingsdaten zufällig als Vorverarbeitung gemischt. Um die Verarbeitung zu beschleunigen, haben wir uns außerdem entschlossen, die Daten in die gemeinsam genutzte Variable von Theano aufzunehmen.
def setup_data(xmat, ymat):
# store the data into 'shared' variables to be accessible by Theano
def shared_dataset(xm, ym, borrow=True):
shared_x = theano.shared(np.asarray(xm, dtype=theano.config.floatX),
borrow=borrow)
shared_y = theano.shared(np.asarray(ym, dtype=theano.config.floatX),
borrow=borrow)
#
return shared_x, shared_y
def data_shuffle(xm, ym, siz):
idv = np.arange(siz)
idv0 = np.array(idv) # copy numbers
np.random.shuffle(idv)
xm[idv0] = xm[idv]
ym[idv0] = ym[idv]
return xm, ym
total_len = ymat.shape[0]
n_features = np.size(xmat) / total_len
# Random Shuffle
xmat, ymat = data_shuffle(xmat, ymat, total_len)
train_len = int(total_len * 0.7)
test_len = total_len - train_len
xtr, ytr = shared_dataset((xmat[:train_len]).reshape(train_len, n_features),
ymat[:train_len])
xte, yte = shared_dataset((xmat[train_len:]).reshape(test_len, n_features),
ymat[train_len:])
rval = [(xtr, ytr), (xte, yte)]
return rval
Die Beschreibung der Funktion theano.function wird geändert, da das Speicherziel des Datensatzes in die gemeinsam genutzte Variable verschoben wird. Argumente müssen indirekt mit den Schlüsselwörtern ** givens ** und nicht direkt mit ** Eingaben ** angegeben werden.
Eingabe (Nachdruck) von Daten mit Theano-Variable (nicht gemeinsam genutzte Variable)
# Compile
train = theano.function(
inputs=[x,y],
outputs=[cost, prediction],
updates=((w, w - 0.1 * gw), (b, b - 0.1 * gb)),
allow_input_downcast=True)
predict = theano.function(inputs=[x], outputs=prediction,
allow_input_downcast=True)
Eingabedaten von gemeinsam genutzten Variablen (SGD-Version)
# Compile
batch_size = 10
train_model = theano.function(
inputs=[index, learning_rate],
outputs=[cost, prediction],
updates=((w, w - learning_rate * gw), (b, b - learning_rate * gb)),
givens=[(x, xtr[index * batch_size:(index + 1) * batch_size]),
(y, ytr[index * batch_size:(index + 1) * batch_size])],
allow_input_downcast=True
)
predict = theano.function(
inputs=[],
outputs=prediction,
givens=[(x, xte)],
allow_input_downcast=True
)
Die iterative Berechnung wird mit der oben definierten Theano-Funktion durchgeführt.
# Train (Optimization)
start_time = timeit.default_timer()
n_epochs = 20
epoch = 0
lrate_base = 0.03
lrate_coef = 20
n_train_batches = int(ytr.get_value().shape[0] / batch_size)
while (epoch < n_epochs):
epoch += 1
for mini_batch_index in range(n_train_batches):
l_rate = lrate_base * lrate_coef / (epoch + lrate_coef)
cost_j, pred = train_model(mini_batch_index, l_rate)
print 'epoch[%3d] : cost =%f ' % (epoch, cost_j)
Ausführungsergebnis.
Initial model:
w : [ 0.0000], b : [ 0.0000]
epoch[ 1] : cost =0.503755
epoch[ 2] : cost =0.510341
epoch[ 3] : cost =0.518218
epoch[ 4] : cost =0.524344
epoch[ 5] : cost =0.528745
epoch[ 6] : cost =0.531842
epoch[ 7] : cost =0.534014
epoch[ 8] : cost =0.535539
epoch[ 9] : cost =0.536614
epoch[ 10] : cost =0.537375
epoch[ 11] : cost =0.537913
epoch[ 12] : cost =0.538294
epoch[ 13] : cost =0.538563
epoch[ 14] : cost =0.538751
epoch[ 15] : cost =0.538880
epoch[ 16] : cost =0.538966
epoch[ 17] : cost =0.539021
epoch[ 18] : cost =0.539053
epoch[ 19] : cost =0.539067
epoch[ 20] : cost =0.539069
Final model:
w : [ 0.3680], b : [ -4.9370]
Elapsed time: 26.565 [s]
accuracy = 0.7868
Ich habe die Änderungen der Parameter in der Berechnung aufgezeichnet.
** Abb. Plot für jede Epoche **
** Abb. Plot für jede Mini-Charge **
Wenn die Auflösung erhöht wird, kann die Bewegungscharakteristik der stochastischen Gradientenabstiegsmethode (SGD) beobachtet werden.
Da der Datensatz "Erwachsener" viele unabhängige Variablen (Merkmale) enthält, haben wir beschlossen, die Merkmale für die Berechnung zu erhöhen. Der Code ändert nur die Eingabeverarbeitung der Trainingsdaten x. Die verwendeten Funktionen sind wie folgt.
Ich hatte erwartet, dass sich die Genauigkeit der Klassifizierung in gewissem Maße verbessern würde, aber leider hat sich die Genauigkeit gegenüber dem ersten Regressionsmodell nicht verbessert. (Dieses Mal besteht der Zweck darin, das Programm zu implementieren, daher haben wir die Datenanalyseergebnisse nicht berücksichtigt.)
Die Ergebnisse des Benchmarks bezüglich der Berechnungszeit sind wie folgt.
** Vergleich der Berechnungszeit **
Optimize method | Model feature number | CPU / GPU | epoch number | mini-batch size | time [s] |
---|---|---|---|---|---|
Batch Gradient Descent | 1 | CPU | 10,000 | - | 76.75 |
Batch Gradient Descent | 1 | GPU | 10,000 | - | 91.14 |
Stochastic Gradient Descent | 1 | CPU | 20 | 10 | 1.76 |
Stochastic Gradient Descent | 1 | GPU | 20 | 10 | 23.87 |
Stochastic Gradient Descent | 3 | CPU | 20 | 10 | 4.51 |
Stochastic Gradient Descent | 3 | GPU | 20 | 10 | 88.38 |
In keiner der Berechnungen wird eine Konvergenzbeurteilung durchgeführt. Berechnen Sie die angegebene Anzahl von Schleifen. ! Batch Gradient Descent erforderte ungefähr 10.000 Berechnungen, um eine konvergente Lösung zu erhalten. (Lernrate Lernrate = 0,1)
Wenn Sie sich die GPU-Berechnung nicht ansehen, sparen Sie mit Batch G.D. vs. SGD viel Rechenzeit. Wir konnten die hohe Berechnungseffizienz von SGD bestätigen.
Das Problem ist nun die "ineffiziente Berechnung der GPU". Da die Berechnungszeit durch Einstellen des Timers vor dem Training und Erfassen des Timerwerts nach Abschluss festgelegt wird, besteht kein Zweifel daran, dass dieser Lernteil die Ursache ist. Normalerweise wird vermutet, dass die CPU-Berechnung (insbesondere die Numpy-Verarbeitung) im GPU-Berechnungsteil gemischt ist. In diesem Sinne habe ich mich im Code umgesehen, aber die Ursache nicht gefunden. (Eigentlich beziehe ich mich auf den Code in der Dokumentation zu Theano Tutorial, Deep Learning 0.1, der ein Modell ist, also glaube ich nicht, dass ich einen einfachen Fehler machen kann.)
Danach kam ich auf den Aufwand, Theano Function aufzurufen. Ich habe die Mini-Batch-Größe geändert (erhöht) und die Berechnungszeit gemessen.
Die horizontale Achse ist die Mini-Batch-Größe und die vertikale Achse ist die Trainingszeit. Die Skala links ist linear-linear und die Skala rechts ist log-linear. Es ist zu berücksichtigen, dass die Anzahl der Schleifen proportional zur Mini-Batch-Größe abnimmt. Das obige Ergebnis zeigt jedoch, dass die Berechnungszeit "exponentiell" reduziert wird und dass der Einfluss des Trainingsfunktionsaufrufs groß ist.
In der Vorlesung von Coursera wurde erklärt, dass "die Größe des Mini-Batches unter Berücksichtigung der parallelen Berechnung (Vektorisierung) des Prozessors festgelegt werden sollte, etwa 2 bis 100 sind praktisch". Darüber hinaus scheint es einen Vorschlag zu geben, dass "im Fall der Klassenklassifizierung eine Entscheidung nach der Anzahl der Klassen des Sortierziels angebracht ist (2, da diesmal 2 Klassifizierungen sind, 10 für die handschriftliche MNIST-Nummernklassifizierung). Aus dem Ergebnis von "Es ist besser, die Größe von Mini-Batch in gewissem Maße in der GPU-Berechnung festzulegen".
Da es sich diesmal um eine logistische Regression handelt, ist der Rechenaufwand pro Charge erheblich geringer als der eines neuronalen Netzes. Ich möchte die Auswirkung der Mini-Batch-Größe auf eine etwas größere Berechnung wie ein neuronales Netz zu einem späteren Zeitpunkt untersuchen. Darüber hinaus ist der Overhead des Funktionsaufrufs auf die Datenübertragung zwischen Speichern zurückzuführen, sodass die Situation je nach Hardware unterschiedlich sein kann. (Ist es mit Laptop PC unmöglich?)
(Die Programmierumgebung für diesen Artikel lautet wie folgt: Python 2.7.8, Theano 0.7.0, CUDA Driver / Runtime 7.5 / 7.0)
In dem obigen Artikel schrieb ich: "Wenn ich die probabilistische Gradientenabstiegsmethode mit Mini-Batch durchführe, scheint sie von der Mini-Batch-Größe beeinflusst zu werden." Da ich jedoch einen Kommentar dazu erhalten habe, habe ich die Bedingungen und den Benchmark-Test erhöht Ich habe es versucht.
Wie in diesem Artikel habe ich "Adult" aus dem UCI Machine Learning-Repository ausgewählt und verwendet. Daten für "Erwachsene" sind ein Problem bei der Klassifizierung des Jahreseinkommens von "50.000 USD" oder weniger und "50.000 USD" oder mehr basierend auf der "Familienstruktur" und dem "Bildungshintergrund" der amerikanischen Einwohner. Dieses Mal haben wir zwei Klassifizierungscodes verwendet.
Klassifizierung nach logistischer Regression Erstellen Sie ein Regressionsmodell, indem Sie 3 der 14 im Datensatz "Erwachsener" enthaltenen Funktionen auswählen. Außerdem werden die Daten in der Datei "adult.data" in 70% / 30% unterteilt und für Zugdaten bzw. Testdaten verwendet. (Beim letzten Mal habe ich die obige Operation ausgeführt, ohne die Existenz der im Datensatz enthaltenen Testdatei 'adult.test' zu bemerken.)
Klassifizierung nach dem MLP-Modell (Multi-Layer Perceptron). Wählen Sie 11 der 14 Funktionen aus, die im Datensatz "Erwachsene" enthalten sind, und geben Sie sie in das MLP-Netzmodell ein. Das MLP besteht aus versteckter Schicht 1 (22 Einheiten) + versteckter Schicht 2 (20 Einheiten) + Ausgabeschicht (1 Einheit). Die Datei "adult.data" wurde als Zugdaten und "adult.test" als Testdaten verwendet. Die Anzahl der Instanzen ist Train-32561, Test-16281.
Der Optimierer verwendete die Methode des stochastischen Gradientenabfalls, bei der die Parameter angepasst werden, während Daten mit einem Mini-Batch geliefert werden.
Die Trainingsdaten werden als ein Satz festgelegt und nach Aufteilung in eine vorgegebene Mini-Batch-Größe in den Klassifizierer eingegeben. Der Berechnungsschritt zur Eingabe des gesamten Satzes wird als Epoche bezeichnet, und die feste Anzahl von Epochen (diesmal Epoche = 50) wurde berechnet, ohne eine Konvergenzbeurteilung durchzuführen. Unten ist der Code für diesen Teil.
#############################################
batch_size = 100
#############################################
# Compile
train_model = theano.function(
inputs=[index],
outputs=[cost, accur],
updates=one_update,
givens=[(x, trXs[index * batch_size:(index + 1) * batch_size]),
(y_, trYs[index * batch_size:(index + 1) * batch_size])],
allow_input_downcast=True
)
accuracy = theano.function(
inputs=[],
outputs=accur,
givens=[(x, teXs), (y_, teYs)],
allow_input_downcast=True
)
# Train (Optimization)
start_time = timeit.default_timer()
n_epochs = 50
epoch = 0
n_train_batches = int(trY.shape[0] / batch_size)
while (epoch < n_epochs):
epoch += 1
for mini_batch_index in range(n_train_batches):
cost_j, accur = train_model(mini_batch_index)
print('epoch[%3d] : cost =%8.4f' % (epoch, cost_j))
elapsed_time = timeit.default_timer() - start_time
print('Elapsed time: %10.3f [s]' % elapsed_time)
last_accur = accuracy()
print('Accuracy = %10.3f ' % last_accur)
Eine Einschränkung ist die Anzahl der Mini-Batches in einer Epoche.
# Mini-Chargenanzahl=Anzahl der Zugdateninstanzen/ Mini-Chargengröße
n_train_batches = int(trY.shape[0] / batch_size)
In einigen Fällen wird der Überschuss abgeschnitten. Dies hat einen relativ großen Effekt, wenn die Mini-Batch-Größe zunimmt. Im Fall von 32.561 Mini-Batch-Größe 10000 werden beispielsweise 30.000 Instanzen referenziert, 2561 jedoch übersprungen.
Die Computerumgebung ist wie folgt.
** Testergebnis (Rohdaten) ** (Einheit ist Sekunden [s])
batch_siz | Laptop_LR_fastc | Laptop_MLP_fastc | Laptop_LR_fastr | Laptop_MLP_fastr | Desktop_LR_fastr | Desktop_MLP_fastr |
---|---|---|---|---|---|---|
10 | 113.3 | 1546.6 | 108.8 | 362.7 | 15.3 | 57.4 |
20 | 56.9 | 758.6 | 55.5 | 176.1 | 8.0 | 28.5 |
50 | 22.6 | 321.6 | 22.2 | 91.4 | 3.2 | 16.6 |
100 | 11.6 | 159.8 | 11.5 | 47.0 | 3.1 | 8.6 |
200 | 6.2 | 77.0 | 5.9 | 23.8 | 1.6 | 4.5 |
500 | 4.4 | 30.6 | 4.3 | 7.9 | 1.0 | 1.8 |
1000 | 2.2 | 15.4 | 2.3 | 4.6 | 0.5 | 1.2 |
2000 | 1.2 | 9.3 | 1.3 | 3.5 | 0.3 | 0.9 |
5000 | 0.4 | 4.6 | 0.5 | 1.9 | 0.2 | 0.6 |
10000 | 0.3 | 4.0 | 0.4 | 1.6 | 0.1 | 0.5 |
Beschreibung jeder Spalte:
--batch_siz
: Mini-Batch-Größe
--Laptop_LR_fastc
: Logistische Regression auf einem Laptop-PC, theano.config.Mode = fast_compile
--Laptop_MLP_fastc
: MLP-Modellklassifizierung auf einem Laptop-PC, theano.config.Mode = fast_compile
--Laptop_LR_fastr
: Logistische Regression auf dem Laptop-PC, theano.config.Mode = fast_run
--Laptop_MLP_fastr
: MLP-Modellklassifizierung auf dem Desktop-PC, theano.config.Mode = fast_run
--Desktop_LR_fastr
: Logistische Regression auf dem Desktop-PC, theano.config.Mode = fast_run
--Desktop_MLP_fastr
: MLP-Modellklassifizierung auf dem Desktop-PC, theano.config.Mode = fast_run
'theano.config.Mode' ist eine Option für'fast_run ', um die Optimierungsstufe zu erhöhen und die Ausführungsgeschwindigkeit zu erhöhen, und' fast_compile 'ist eine Option für die teilweise Optimierung (Verkürzung der Kompilierungszeit).
Als nächstes werden wir uns die Details ansehen, während wir uns auf die Handlung beziehen.
Fig. Logistic Regression vs. MLP model
(Laptop_LR_fastr vs. Laptop_MLP_fastr)
Die horizontale Achse ist die Mini-Batch-Größe und die vertikale Achse ist die Zeit, die für den Lernteil benötigt wird. Erstens der Unterschied im Klassifizierungscode und der Vergleich zwischen logistischer Regression und Klassifizierung nach MLP-Modell. Wie erwartet ist die Berechnungszeit aufgrund der Zunahme des Rechenaufwands im MLP-Modell etwa drei- bis viermal länger. Darüber hinaus ist der Einfluss der Mini-Batch-Größe für beide gleich, und es ist ersichtlich, dass die Berechnungszeit mit zunehmender Mini-Batch-Größe abnimmt.
Fig. Theano mode FAST_COMPILE vs. FAST_RUN (Logistic Regression)
Dies ist ein Vergleich zwischen dem Modus "FAST_COMPILE", der nicht viel CUDA-bezogene Optimierung durchführt, und dem Modus "FAST_RUN", der mehr Optimierung durchführt, aber wie in der obigen Abbildung gezeigt, gibt es keinen großen Unterschied zwischen logistischen Regressionen.
Fig. Theano mode FAST_COMPILE vs. FAST_RUN (MLP classification)
Andererseits hat sich bei der Klassifizierung von MLP-Modellen mit einem hohen Rechenaufwand der optimierte Effekt von "FAST_RUN" herausgestellt, was zu einer Verkürzung der Berechnungszeit führt.
FIG. Laptop PC vs. Desktop PC (MLP classification)
Es wird angenommen, dass dies das Ergebnis eines einfachen Unterschieds in der Hardwareleistung ist. (In beiden Fällen ist der Theano-Modus "FAST_RUN". Außerdem habe ich den Unterschied im Betriebssystem nicht im Detail untersucht, aber der Effekt wird gering sein.)
Wie oben erwähnt, wurde beobachtet, dass die Lernberechnungszeit tendenziell signifikant abnimmt, wenn die Mini-Batch-Größe unter allen Bedingungen zunimmt. Die Ursache ist, dass bei einer kleinen Gravur der Mini-Batch-Größe die Anzahl der Aufrufe der Funktion "train_model ()" in der "while" -Lernschleife zunimmt und der Einfluss des Overheads auf diesen Funktionsaufruf als groß angesehen wird. (Wenn Sie genauer nachforschen möchten, müssen Sie meines Erachtens einen Profiler verwenden. Vorerst habe ich die Situation mit dem C-Profil des Standardprofilers betrachtet, aber ich konnte den Teil erfassen, der im Teil des Theano-Codes Zeit in Anspruch nahm. Aufgrund mangelnder Fähigkeiten habe ich jedoch auf die Details verzichtet.)
Bei diesem Test (wie oben erwähnt, besteht das Problem des "Abschneidens" der Daten, die während der Datenzufuhr auftreten) sind der Umriss und die zu fütternde Datenmenge dieselben Bedingungen. Ursprünglich geht es zum Zeitpunkt des Lernens darum, die Genauigkeit des Klassifikators so schnell wie möglich zu verbessern, sodass eine Strategie zur Anpassung der Berechnungsparameter (Lernrate, Optimierungsparameter usw.) für jeden Mini-Batch festgelegt werden kann. Es gibt viele. Es ist wichtig, die Größe des Mini-Batch unter Berücksichtigung dieser Angelegenheit und des Overheads, der entsteht, wenn die so genannte GPU-Berechnungsfunktion eingehalten wird, angemessen einzustellen, um ein effizientes Lernen zu realisieren.
Recommended Posts