Instanzen vs. Kerne bei Verwendung von EC2

12

Ich arbeitete an Projekten, die oft als "mittlere Daten" bezeichnet werden, und konnte meinen Code (hauptsächlich für die Modellierung und Vorhersage in Python) auf einem einzelnen System mit 4 bis 32 Kernen parallelisieren. Jetzt möchte ich auf Cluster unter EC2 hochskalieren (wahrscheinlich mit StarCluster / IPython, aber offen für andere Vorschläge) und bin ratlos darüber, wie die Verteilung der Arbeit auf Kerne auf eine Instanz im Vergleich zu Instanzen auf einem Cluster abgestimmt werden kann.

Ist es überhaupt praktisch, instanz- und kernübergreifend zu parallelisieren? Wenn ja, kann jemand einen kurzen Überblick über die Vor- und Nachteile der Ausführung vieler Instanzen mit jeweils wenigen Kernen im Vergleich zu einigen Instanzen mit vielen Kernen geben? Gibt es eine Faustregel für die Auswahl des richtigen Verhältnisses von Instanzen zu Kernen pro Instanz?

Bandbreite und Arbeitsspeicher sind in meinen Projekten keine trivialen Probleme, aber es ist leicht zu erkennen, wann dies die Engpässe sind und sich neu einstellen. Ich würde mir vorstellen, dass es viel schwieriger ist, die richtige Mischung von Kernen mit Instanzen ohne wiederholte Tests zu vergleichen, und meine Projekte variieren zu sehr, als dass ein einzelner Test auf alle Umstände anwendbar wäre. Vielen Dank im Voraus, und wenn ich es gerade nicht geschafft habe, diese Seite richtig zu googeln, können Sie mich gerne auf die richtige Antwort verweisen!

Therriault
quelle

Antworten:

11

Wenn Sie IPython verwenden, müssen Sie sich beinahe keine Sorgen machen (auf Kosten eines gewissen Effizienzverlusts / eines höheren Kommunikationsaufwands). Das parallele IPython-Plugin in StarCluster startet standardmäßig eine Engine pro physischem Kern auf jedem Knoten (ich glaube, dies ist konfigurierbar, aber nicht sicher, wo). Mit der DirectView-API (map_sync, apply_sync, ...) oder den magischen% px-Befehlen können Sie einfach alle Module ausführen, die Sie möchten. Wenn Sie IPython bereits parallel auf einem Computer verwenden, ist die Verwendung in einem Cluster nicht anders.

Beantworten einiger Ihrer spezifischen Fragen:

"Wie wird die Verteilung der Arbeit auf mehrere Kerne einer Instanz im Vergleich zu Instanzen in einem Cluster abgestimmt?" - Sie erhalten (mindestens) eine Engine pro Kern. Die Arbeit wird automatisch auf alle Kerne und Instanzen verteilt.

"Ist es überhaupt praktisch, eine Parallelisierung zwischen Instanzen sowie zwischen Kernen auf jeder Instanz durchzuführen?" - Ja :) Wenn der Code, den Sie ausführen, auf peinliche Weise parallel ist (exakt derselbe Code für mehrere Datensätze), können Sie meistens ignorieren, wo eine bestimmte Engine ausgeführt wird. Wenn der Kern viel Kommunikation zwischen Engines erfordert, müssen Sie ihn natürlich so strukturieren, dass Engines in erster Linie mit anderen Engines auf derselben physischen Maschine kommunizieren. aber diese Art von Problem ist nicht ideal für IPython geeignet, denke ich.

"Wenn ja, kann jemand einen kurzen Überblick über die Vor- und Nachteile der Ausführung mehrerer Instanzen mit jeweils wenigen Kernen im Vergleich zu einigen Instanzen mit mehreren Kernen geben? Gibt es eine Faustregel für die Auswahl des richtigen Verhältnisses von Instanzen zu Kernen pro Instanz? " - Verwenden Sie die größten c3-Instanzen für rechnergebundene und die kleinsten für speicherbandbreitengebundene Probleme. Verwenden Sie bei Problemen mit der Nachrichtenübermittlung auch die größten Instanzen, aber versuchen Sie, das Problem so zu partitionieren, dass jede Partition auf einem physischen Computer ausgeführt wird und sich die meisten Probleme mit der Nachrichtenübermittlung in derselben Partition befinden. Probleme, die auf N vierfachen c3-Instanzen erheblich langsamer ablaufen als auf 2N doppelten c3-Instanzen, sind selten (ein künstliches Beispiel könnte darin bestehen, mehrere einfache Filter für eine große Anzahl von Bildern auszuführen, bei denen Sie alle Bilder für jeden Filter und nicht alle Filter für den Filter durchlaufen gleiches Bild).

Alex ich
quelle
1
Ich denke, Sie sollten beachten, dass Sie für Prozesse auf einem einzelnen Computer Variablen mit joblib / Numpy speichern können. Sie verlieren diese Fähigkeit für Prozesse auf verschiedenen Computern.
Gallamine
11

Eine allgemeine Faustregel lautet, erst dann zu verbreiten, wenn Sie es müssen. In der Regel ist es effizienter, N Server mit einer bestimmten Kapazität zu haben, als 2N Server mit der Hälfte dieser Kapazität. Der Datenzugriff erfolgt mehr lokal und ist daher im Arbeitsspeicher schnell als im Netzwerk langsam.

Ab einem bestimmten Punkt wird die Skalierung einer Maschine unwirtschaftlich, da die Kosten für zusätzliche Ressourcen mehr als linear ansteigen. Dieser Punkt ist jedoch immer noch erstaunlich hoch.

Insbesondere bei Amazon kann die Wirtschaftlichkeit der einzelnen Instanztypen stark variieren, wenn Sie Instanzen für den Spotmarkt verwenden. Der Standardpreis bedeutet, dass unabhängig vom Instanztyp ungefähr die gleiche Menge an Ressourcenkosten anfällt, die sehr unterschiedlich sein können. Große Instanzen können billiger sein als kleine, oder N kleine Instanzen können viel billiger sein als eine große Maschine mit äquivalenten Ressourcen.

Eine wichtige Überlegung hierbei ist, dass sich das Berechnungsparadigma erheblich ändern kann, wenn Sie von einer Maschine zu mehreren Maschinen wechseln. Die Kompromisse, die der Kommunikationsaufwand mit sich bringt, können Sie beispielsweise dazu zwingen, ein datenparalleles Skalierungsparadigma einzuführen. Das bedeutet eine andere Auswahl an Werkzeugen und Algorithmen. Beispielsweise sieht SGD im Arbeitsspeicher und in Python ganz anders aus als in MapReduce. Sie müssten dies also berücksichtigen, bevor Sie parallelisieren.

Sie können sich aus Gründen der Zuverlässigkeit dafür entscheiden, die Arbeit auf einen Cluster zu verteilen, auch wenn ein einzelner Knoten und nicht verteilte Paradigmen für Sie funktionieren. Wenn ein einzelner Knoten ausfällt, verlieren Sie die gesamte Berechnung. Eine verteilte Berechnung kann möglicherweise nur den Teil der Berechnung wiederherstellen und vervollständigen, der verloren gegangen ist.

Sean Owen
quelle
6

Wenn alle Faktoren gleich sind (Kosten, CPU-Leistung usw.), können Sie die kleinste Instanz auswählen, die alle meine Datenmengen speichern und skalieren kann. Dieser Weg

  • Sie stellen sicher, dass durch die Netzwerkkommunikation keine unnötigen Latenzen entstehen, und
  • Sie neigen dazu, die insgesamt verfügbare Speicherbandbreite für Ihre Prozesse zu maximieren.

Angenommen, Sie führen eine Art Kreuzvalidierungsschema aus , um einige Metaparameter Ihres Modells zu optimieren , weisen Sie jedem Kern einen zu testenden Wert zu und wählen Sie nach Bedarf viele Instanzen aus, um den gesamten Parameterraum in so wenigen Runden abzudecken, wie Sie es für richtig halten.

Wenn Ihre Daten nicht in den Speicher eines Systems passen, müssen Sie sie natürlich auf mehrere Instanzen verteilen. Dann geht es darum, die Speicherlatenz (bei vielen Instanzen besser) mit der Netzwerklatenz (bei weniger Instanzen besser) in Einklang zu bringen. Angesichts der Natur von EC2 würde ich wetten, dass Sie es oft vorziehen, mit wenigen fetten Instanzen zu arbeiten.

damienfrancois
quelle