OpenAI: Vier grundlegende Methoden zum Training großer neuronaler Netze

WBOY
Freigeben: 2023-04-10 09:41:07
nach vorne
1127 Leute haben es durchsucht

OpenAI: Vier grundlegende Methoden zum Training großer neuronaler Netze

Dieser Artikel wurde von Lei Feng.com reproduziert. Wenn Sie einen Nachdruck benötigen, besuchen Sie bitte die offizielle Website von Lei Feng.com, um eine Genehmigung zu beantragen.

Große neuronale Netze sind eines der aktuellen Themen im Bereich der künstlichen Intelligenz. Wie trainiert man also große Modelle?

Kürzlich hat OpenAI, das das groß angelegte Vortrainingsmodell GPT-3 auf den Markt gebracht hat, einen Blogbeitrag veröffentlicht, in dem vier speichersparende parallele Trainingsmethoden auf GPU-Basis vorgestellt werden:

  • Datenparallel— – Führen Sie verschiedene Teilmengen desselben Stapels auf verschiedenen GPUs aus.
  • Pipeline-Parallelität – führen Sie verschiedene Ebenen des Modells auf verschiedenen GPUs aus die GPU;
  • Expertenmix (MOE) – Verarbeiten Sie jedes Beispiel nur durch einen kleinen Teil jeder Ebene.

OpenAI: Vier grundlegende Methoden zum Training großer neuronaler NetzeBildunterschrift: Verschiedene parallele Strategien beim Dreischichtmodell, jede Farbe stellt eine Schicht dar und gepunktete Linien trennen verschiedene GPUs.

1 Datenparallel

„Datenparalleles Training“ bedeutet, dieselben Parameter auf mehrere GPUs (oft als „Worker“ bezeichnet) zu kopieren und jeder GPU unterschiedliche Beispiele zur gleichzeitigen Verarbeitung zuzuweisen.

Allein die Datenparallelität erfordert, dass das Modell in einen einzigen GPU-Speicher passt. Wenn Sie jedoch mehrere GPUs für die Berechnung nutzen, entstehen Kosten für die Speicherung mehrerer Kopien der Parameter. Allerdings gibt es Strategien zur Erhöhung des effektiven RAM, der der GPU zur Verfügung steht, wie z. B. die vorübergehende Auslagerung von Parametern in den CPU-Speicher zwischen den Nutzungen.

Da jeder Data Parallel Worker seine Parameterkopie aktualisiert, müssen sie sich untereinander koordinieren, um sicherzustellen, dass jeder Worker weiterhin über ähnliche Parameter verfügt. Die einfachste Methode besteht darin, eine „blockierende Kommunikation“ zwischen Arbeitern einzuführen:

Schritt 1: Berechnen Sie den Gradienten für jeden Arbeiter unabhängig.

Schritt 2: Durchschnitten Sie den Gradienten verschiedener Arbeiter die gleichen neuen Parameter unabhängig für jeden Worker.

Schritt 2 ist ein blockierender Durchschnitt, der die Übertragung einer großen Datenmenge erfordert (proportional zur Anzahl der Arbeiter mal der Parametergröße), was den Durchsatz des Trainings beeinträchtigen kann. Es gibt verschiedene asynchrone Synchronisationsschemata, die diesen Verlust beseitigen können, allerdings auf Kosten der Lerneffizienz, sodass man in der Praxis im Allgemeinen bei synchronen Methoden bleibt.

2 Der Speicher wird proportional reduziert.

Ein großes Modell in Teile aufeinanderfolgender Schichten aufzuteilen ist einfach, aber da es sequentielle Abhängigkeiten zwischen den Eingaben und Ausgaben einer Schicht gibt, ist es naiv, darauf zu warten, dass die Ausgabe der vorherigen Maschine als Eingabe verwendet wird. Die Ausführung von kann zu erheblicher Leerlaufzeit führen. Diese Wartezeitblöcke werden „Blasen“ genannt und sind verschwendete Berechnungen, die von inaktiven Maschinen durchgeführt werden könnten.

Bildunterschrift: Abbildung eines einfachen Pipeline-Parallelaufbaus, bei dem das Modell vertikal in 4 Partitionen unterteilt ist. Worker 1 hostet die Modellparameter von Ebene 1 (am nächsten zur Eingabe), während Worker 4 Ebene 4 (am nächsten zur Ausgabe) hostet. „F“, „B“ und „U“ stehen jeweils für Vorwärts-, Rückwärts- und Aktualisierungsvorgänge. Der Index gibt an, auf welchem ​​Worker die Operation ausgeführt werden soll. Aufgrund sequenzieller Abhängigkeiten werden Daten jeweils von einem Worker verarbeitet, was zu großen „Blasen“ in der Leerlaufzeit führt.

Wir können die Idee der Datenparallelität wiederverwenden, um die Kosten für die Entstehung von Zeitblasen zu reduzieren, indem jeder Worker jeweils nur eine Teilmenge von Datenelementen verarbeitet, was es uns ermöglicht, neue Berechnungen geschickt mit Wartezeiten zu überlagern. Die Kernidee besteht darin, dass durch die Aufteilung eines Batches in mehrere Mikrobatches jeder Mikrobatch proportional schneller verarbeitet werden sollte und jeder Arbeiter mit der Arbeit beginnen sollte, sobald der nächste Mikrobatch verfügbar ist, wodurch die Pipeline-Implementierung beschleunigt wird. Bei genügend Mikrochargen können die Arbeitskräfte die meiste Zeit genutzt werden, mit minimalen „Blasen“ am Anfang und am Ende der Schritte. Die Gradienten werden über Mikrobatches hinweg gemittelt und die Parameter werden erst aktualisiert, nachdem alle Mikrobatches abgeschlossen sind.

Die Anzahl der in ein Modell aufgeteilten Arbeiter wird oft als „Pipeline-Tiefe“ bezeichnet.

Während des Vorwärtsdurchlaufs sendet ein Arbeiter nur die Ausgaben seiner Schichtblöcke (genannt „Aktivierungen“) an den nächsten Arbeiter, während er beim Rückwärtsdurchlauf nur die Steigungen dieser Aktivierungen an das Personal des vorherigen Arbeiters sendet. Es gibt einen großen Gestaltungsspielraum bei der Anordnung dieser Kanäle und der Aggregation von Farbverläufen über Mikrobatches hinweg. Beispielsweise lässt die Methode GPipe jeden Worker-Prozess kontinuierlich vorwärts und rückwärts durchlaufen und aggregiert dann am Ende synchron die Farbverläufe aus mehreren Mikrobatches, während PipeDream dafür sorgt, dass jeder Worker abwechselnd Vorwärts- und Rückwärtsdurchläufe verarbeitet.

OpenAI: Vier grundlegende Methoden zum Training großer neuronaler Netze

OpenAI: Vier grundlegende Methoden zum Training großer neuronaler Netze

Bildunterschrift: Vergleich der GPipe- und PipeDream-Pipeline-Schemata unter Verwendung von 4 Mikrobatches pro Batch. Die Mikrobatches 1–8 entsprechen zwei aufeinanderfolgenden Datenbatches. Die „Nummer“ in der Abbildung gibt an, an welcher Mikrocharge gearbeitet wird, und der Index markiert die Arbeiter-ID. Beachten Sie, dass PipeDream eine höhere Effizienz erzielt, indem es einige Berechnungen mit veralteten Parametern durchführt.

3

Bei vielen modernen Modellen (z. B. Transformer) besteht der rechnerische Engpass darin, die Aktivierungs-Batch-Matrix mit einer großen Gewichtsmatrix zu multiplizieren. Die Matrixmultiplikation kann als Skalarprodukt zwischen Zeilen- und Spaltenpaaren betrachtet werden; die Skalarprodukte können unabhängig auf verschiedenen GPUs berechnet werden, oder jeder Teil des Skalarprodukts kann auf verschiedenen GPUs berechnet und die Ergebnisse summiert werden. Unabhängig von der Strategie können wir die Gewichtsmatrix in gleichmäßig große „Shards“ aufteilen, jeden Shard auf einer anderen GPU hosten und diesen Shard verwenden, um den relevanten Teil des gesamten Matrixprodukts zu berechnen, bevor wir ihn an das Kombinationsergebnis weitergeben.

Ein Beispiel ist Megatron-LM, das die Matrixmultiplikation innerhalb der Selbstaufmerksamkeits- und MLP-Schichten des Transformers parallelisiert. PTD-P nutzt Tensor-, Daten- und Pipeline-Parallelität, und sein Pipeline-Scheduling weist jedem Gerät mehrere diskrete Schichten zu, um Blasenverluste auf Kosten einer verbesserten Netzwerkkommunikation zu reduzieren.

Manchmal können Netzwerkeingaben dimensionübergreifend parallelisiert werden, wobei im Vergleich zur Querkommunikation ein hoher Grad an paralleler Berechnung vorliegt. Sequenzparallelität ist die Idee, bei der eine Eingabesequenz zeitlich in mehrere Unterbeispiele unterteilt wird, wodurch der Spitzenspeicherverbrauch proportional reduziert wird, indem die Berechnung an feinkörnigeren Beispielen fortgesetzt werden kann.

4

Ein Beispielansatz besteht darin, über mehrere Gewichtssätze zu verfügen, und das Netzwerk kann über einen Gating-Mechanismus auswählen, welcher Gewichtssatz zur Inferenzzeit verwendet werden soll, was mehr Parameter ermöglicht, ohne den Rechenaufwand zu erhöhen. Jeder Gewichtssatz wird als „Experte“ bezeichnet, und die Hoffnung besteht darin, dass das Netzwerk lernt, jedem Experten spezielle Berechnungen und Fähigkeiten zuzuweisen. Verschiedene Experten können unterschiedliche GPUs hosten und bieten so eine klare Möglichkeit, die Anzahl der für ein Modell verwendeten GPUs zu skalieren.

Legende: Das Gated Network wählt nur 2 von n Experten aus.

GShard erweitert die Parameter von MoE Transformer auf 600 Milliarden Parameter, wobei nur die MoE-Schicht in mehrere TPU-Geräte aufgeteilt ist und andere Schichten Exact sind Kopie. Switch Transformer skaliert die Modellgröße auf Billionen von Parametern mit höherer Sparsity, indem eine Eingabe an einen einzelnen Experten weitergeleitet wird.

5 Andere speichersparende Designs

Es gibt viele andere Berechnungsstrategien, die das Training effizienter machen können Größere neuronale Netze sind einfacher zu verarbeiten. Zum Beispiel:

Um den Gradienten zu berechnen, muss die ursprüngliche Aktivierung gespeichert werden, was viel Geräte-RAM verbraucht. Checkpointing (auch Aktivierungsneuberechnung genannt) speichert jede Teilmenge von Aktivierungen und berechnet während eines Rückwärtsdurchlaufs rechtzeitig Zwischenaktivierungen neu, wodurch erheblich Speicher gespart wird und der Rechenaufwand für höchstens einen zusätzlichen vollständigen Vorwärtsdurchlauf anfällt. Man kann die Rechen- und Speicherkosten auch kontinuierlich ausgleichen, indem man die Neuberechnung selektiv aktiviert. Dabei wird eine Teilmenge von Aktivierungen überprüft, für die die Speicherkosten relativ hoch, die Rechenkosten jedoch niedrig sind.

Beim gemischten Präzisionstraining werden niedrigere Präzisionszahlen (am häufigsten FP16) zum Trainieren des Modells verwendet. Moderne Beschleuniger können mit niedrigeren Präzisionszahlen höhere FLOP-Zahlen erreichen und außerdem Geräte-RAM einsparen. Bei entsprechender Sorgfalt kann das resultierende Modell praktisch ohne Genauigkeitsverlust hergestellt werden.

Offloading ist das vorübergehende Auslagern ungenutzter Daten auf die CPU oder zwischen verschiedenen Geräten und deren Rücklesen bei Bedarf. Eine naive Implementierung verlangsamt das Training erheblich, eine ausgefeilte Implementierung ruft die Daten jedoch vorab ab, sodass das Gerät nie warten muss. Eine Umsetzung dieser Idee ist ZeRO, das Parameter, Verläufe und Optimiererstatus auf die gesamte verfügbare Hardware aufteilt und sie nach Bedarf verfeinert.

Speichereffiziente Optimierer wurden vorgeschlagen, um den Speicherbedarf des vom Optimierer verwalteten Betriebszustands zu reduzieren, wie z. B. Adafactor.

Komprimierung kann auch verwendet werden, um Zwischenergebnisse im Netzwerk zu speichern. Gist komprimiert beispielsweise die für Rückwärtsdurchläufe gespeicherten Aktivierungen; DALL-E komprimiert Farbverläufe, bevor sie synchronisiert werden.

Das obige ist der detaillierte Inhalt vonOpenAI: Vier grundlegende Methoden zum Training großer neuronaler Netze. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!

Verwandte Etiketten:
Quelle:51cto.com
Erklärung dieser Website
Der Inhalt dieses Artikels wird freiwillig von Internetnutzern beigesteuert und das Urheberrecht liegt beim ursprünglichen Autor. Diese Website übernimmt keine entsprechende rechtliche Verantwortung. Wenn Sie Inhalte finden, bei denen der Verdacht eines Plagiats oder einer Rechtsverletzung besteht, wenden Sie sich bitte an admin@php.cn
Beliebte Tutorials
Mehr>
Neueste Downloads
Mehr>
Web-Effekte
Quellcode der Website
Website-Materialien
Frontend-Vorlage