In der Jupyter Notebook-Umgebung namens Colaboratory, an der ich mich schon lange interessiert hatte, habe ich nur versucht, GAN auszuführen, an dem ich mich schon lange interessiert hatte.
In Bezug auf Colavoratory war der Artikel [Verwenden Sie eine kostenlose GPU mit Geschwindigkeit pro Sekunde] Tipps zum Deep Learning-Üben für Colaboratory hilfreich.
Für GAN habe ich einen kurzen Blick auf Article Generative Adversarial Networks geworfen. GAN ist eine Art Methode, die sich der Wahrscheinlichkeitsverteilung der vorliegenden Daten annähert (als gleichmäßige Verteilung betrachtet). Wenn die beiden Netzwerke G und D gut trainiert sind, ist die Wahrscheinlichkeitsverteilung der von G erzeugten Daten verfügbar. Es scheint mit der Wahrscheinlichkeitsverteilung der Daten übereinzustimmen. Es ist möglicherweise nicht möglich, auf gute Weise zu lernen, daher suchen wir derzeit nach Möglichkeiten, dies zu tun.
Für den GAN-Code habe ich auf [hier] verwiesen (https://github.com/eriklindernoren/Keras-GAN/tree/master/gan). GAN wurde einfach mit Keras codiert und es war eine Lernerfahrung.
Es werden zwei MLPs definiert (dies sind G und D), die Ausgabe von G wird an D gegeben und Adam trainiert sie abwechselnd. D lernt, zwischen "vorliegenden Daten" und "Ausgabe von G" zu unterscheiden. G trainiert durch Manipulieren der Lehrerdaten, so dass das Diskriminierungsergebnis von D "die vorliegenden Daten" wird. Zu diesem Zeitpunkt ist D nicht trainiert. Die Trainingsdaten sind MNIST.
Wenn Sie glauben, dass es eine ReLU gibt, mit der Sie nicht vertraut sind, scheint sie Leaky ReLU zu heißen, die heutzutage häufig verwendet wird. (Referenz: Informationen zur Aktivierungsfunktion ReLU und zum ReLU-Clan [zusätzliche Informationen]) Im Gegensatz zu ReLU ist x * α, selbst wenn der Eingang x der Aktivierungsfunktion 0 oder weniger ist Der Wert von wird ausgegeben. Es wird gesagt, dass es für das Wiki nicht effektiv ist, aber ist es möglich, das Verschwinden des Gradienten so weit wie möglich zu reduzieren? Ich bin mir nicht sicher.
Der Code lief ohne Probleme, aber ich trainiere, indem ich train_on_batch in meiner eigenen Schleife anstelle von fit ausführe, sodass kein Verlauf zurückgegeben wird. Ich möchte Verlust und Zugriff visualisieren, daher füge ich Code hinzu, um ihn als Instanzvariable und Code für die Visualisierung zu speichern.
# save
self.all_d_loss_real.append(d_loss_real)
self.all_d_loss_fake.append(d_loss_fake)
self.all_g_loss.append(g_loss)
if epoch % sample_interval == 0:
self.sample_images(epoch)
np.save('d_loss_real.npy', self.all_d_loss_real)
np.save('d_loss_fake.npy', self.all_d_loss_fake)
np.save('g_loss.npy', self.all_g_loss)
real ist der D-Verlust der vorliegenden Daten, und fake ist der D-Verlust der von G. erzeugten Daten. Code zum lokalen Speichern.
from google.colab import files
import os
file_list = os.listdir("images")
for file in file_list:
files.download("images"+os.sep+file)
files.download('d_loss_real.npy')
files.download('d_loss_fake.npy')
files.download('g_loss.npy')
Es ist ein Code zum Zeichnen von Verlusten und so weiter.
import numpy as np
import pylab as plt
t1 = np.load('d_loss_real.npy')
t2 = np.reshape(np.load('d_loss_fake.npy'),[np.shape(t1)[0],2])
g_loss = np.load('g_loss.npy')
t = (t1+t2)/2
d_loss = t[:,0]
acc = t[:,1]
d_loss_real = t1[:,0]
d_loss_fake = t2[:,0]
acc_real = t1[:,1]
acc_fake = t2[:,1]
n_epoch = 29801
x = np.linspace(1,n_epoch,n_epoch)
plt.plot(x, acc, label='acc')
plt.plot(x, d_loss, label='d_loss')
plt.plot(x, g_loss, label='g_loss')
plt.plot(x, d_loss_real, label='d_loss_real')
plt.plot(x, d_loss_fake, label='d_loss_fake')
plt.legend()
plt.ylim([0, 2])
plt.grid()
plt.show()
#gleitender Durchschnitt
num=100#Anzahl der gleitenden Durchschnitte
b=np.ones(num)/num
acc2=np.convolve(acc, b, mode='same')
d_loss2=np.convolve(d_loss, b, mode='same')
d_loss_real2=np.convolve(d_loss_real, b, mode='same')
d_loss_fake2=np.convolve(d_loss_fake, b, mode='same')
g_loss2=np.convolve(g_loss, b, mode='same')
x = np.linspace(1,n_epoch,n_epoch)
plt.plot(x, acc2, label='acc')
plt.plot(x, d_loss2, label='d_loss')
plt.plot(x, g_loss2, label='g_loss')
plt.plot(x, d_loss_real2, label='d_loss_real')
plt.plot(x, d_loss_fake2, label='d_loss_fake')
plt.legend()
plt.ylim([0,1.2])
plt.grid()
plt.show()
Generiertes Bild von G. epoch=0
epoch=200
epoch=1000
epoch=3000
epoch=7000
epoch=10000
epoch=20000
epoch=30000
Mit zunehmender Anzahl von Epochen werden Bilder erzeugt, die MNIST ähnlich sind, aber es scheint, dass sich gegenüber Epoche 7000 keine besonderen Änderungen ergeben werden.
Richtige Antwortrate und Verlust
Gleitender Durchschnitt in der obigen Abbildung (n = 100, an beiden Enden mit Nullen gefüllt)
Ab etwa Epoche 7.000, gem. 0,63, d_loss (auch echt und falsch) 0,63, g_loss 1,02 ~ 1,08 (leichte Zunahme) (d_loss und g_loss sind binäre Kreuzentropie). real ist der D-Verlust der vorliegenden Daten, fake ist der D-Verlust der von G erzeugten Daten und d_loss ist der Durchschnitt.
Verlust ist wie folgt definiert.
\textrm{loss} = -\frac{1}{N}\sum_{n=1}^{N}\bigl( y_n\log{p_n}+(1-y_n)\log{(1-p_n)}\bigr)
N ist die Anzahl der Daten, y ist die Bezeichnung und p ist der Ausgabewert von D (0,1).
Es ist verwirrend, weil es $ \ log $ enthält, aber ich mache die durchschnittliche D-Ausgabe $ \ bigl (\ prod_ {n = 1} ^ {N} p_n ^ {y_n} \ bigr) ^ {\ Ich habe frac {1} {N}} $ in $ \ log $ geändert, und $ \ log $ von 0 auf 1 ist eine negative Zahl und schwer zu erkennen. Deshalb habe ich nur ein Minus hinzugefügt, um daraus eine positive Zahl zu machen.
\begin{align}
\textrm{loss} &= -\frac{1}{N}\sum_{n=1}^{N}\bigl( y_n\log{p_n}+(1-y_n)\log{(1-p_n)}\bigr) \\
&= -\log{\bigl( \prod_{n=1}^{N}p_n^{y_n}\bigr)^{\frac{1}{N}}} -\log{\bigl( \prod_{n=1}^{N}(1-p_n)^{y_n}\bigr)^{\frac{1}{N}}}
\end{align}
◯ Verlust um Epoche 25000
loss | Durchschnittliche D-Ausgabe | |
---|---|---|
g_loss | 1.06 | 0.35 |
d_loss | 0.63 | 0.53 |
d_loss_real | 0.63 | 0.53 |
d_loss_fake | 0.63 | 0.47 |
Je mehr das Etikett mit der Ausgabe übereinstimmt, desto geringer ist der Verlust. GAN zielt nicht darauf ab, Verluste zu reduzieren, daher ist es kein Problem, dass es nicht abnimmt.
Wenn das Lernen gut verläuft und die vorliegenden Daten und die von G erzeugten Daten vollständig nicht unterscheidbar sind (der Zweck von GAN besteht darin, sich in diesem Zustand zu befinden), sollte acc = 0,5 sein, aber soweit das Ergebnis sichtbar ist Es ist nicht.
Wenn man das von G erzeugte Bild betrachtet, scheint es eindeutig keine handgeschriebene Zahl zu sein, was wahrscheinlich der Grund ist, warum acc hoch ist. Es mag ein bisschen besser sein, wenn Sie mit den Parametern spielen, aber da der Zweck nicht darin besteht, hineinzufahren, werde ich hier vorerst aufhören.
Der Wert von g_loss bedeutet, dass je niedriger der Wert von g_loss ist, desto mehr D bestimmt, dass das von G erzeugte Bild wahr ist - das heißt, desto mehr wird D getäuscht. Umgekehrt, je höher der Wert von g_loss ist, desto mehr wird D nicht getäuscht. Wenn das Ziel eine durchschnittliche D-Ausgabe von g_loss von 0,5 ist, dann ist g_loss 0,7, daher möchte ich, dass es etwas weiter abfällt.
Ich glaube nicht, dass acc mit d_loss übereinstimmt.
Ab epoch7000 ~ ist es besorgniserregend, dass das Ausmaß der Abnahme von d_loss_fake kleiner ist als das Ausmaß der Zunahme von g_loss. Selbst bei der durchschnittlichen D-Ausgabe gibt es einen Unterschied von ungefähr dem 10-fachen. Da die Reihenfolge D Lernen → G Lernen ist, ist das für Moro effektiv?
Ich hatte das Gefühl, dass ich es schaffen konnte. Ich glaube nicht, dass etwas besonders verstopft ist, aber da das Labor nicht sehr stabil ist, wird das vergangene Notizbuch aus irgendeinem Grund angezeigt, wenn Sie glauben, dass die Berechnung in der Mitte abstürzt oder der Bildschirm neu geladen wird, und Sie werden es nicht bemerken. Ich habe es überschrieben und den Code schluchzend umgeschrieben.
Seien Sie vorsichtig, wenn dieses Popup nach dem erneuten Laden des Bildschirms von unten angezeigt wird. Wenn Sie sich den Code genau ansehen, handelt es sich um den unbearbeiteten Code unmittelbar nach dem Öffnen von Colaboratory. Wenn Sie ihn speichern, wird er mit dem bearbeiteten Code überschrieben.
Als Gegenmaßnahme denke ich, dass Sie die Seite neu laden sollten. Mein Browser ist Safari, aber wenn ich Strg-R drücke, um die Seite neu zu laden, wird der bearbeitete Code angezeigt und die Variablen nach der Ausführung bleiben ebenfalls erhalten. Wenn dieses Popup angezeigt wird, ist es meiner Meinung nach sicherer, sich nicht zu beeilen, es zu überschreiben.
Ich denke, Sie müssen regelmäßig Backups von Berechnungsabstürzen erstellen.
Recommended Posts