Erlang, Go und Rust behaupten alle auf die eine oder andere Weise, dass sie die gleichzeitige Programmierung mit billigen "Threads" / Coroutinen unterstützen. In den Go-FAQ heißt es:
Es ist praktisch, Hunderttausende von Goroutinen im selben Adressraum zu erstellen.
Das Rust Tutorial sagt:
Da die Erstellung von Tasks erheblich kostengünstiger ist als bei herkömmlichen Threads, kann Rust auf einem typischen 32-Bit-System Hunderttausende von gleichzeitigen Tasks erstellen.
In der Dokumentation von Erlang heißt es:
Die standardmäßige anfängliche Heap-Größe von 233 Wörtern ist recht konservativ, um Erlang-Systeme mit Hunderttausenden oder sogar Millionen von Prozessen zu unterstützen.
Meine Frage: Welche Art von Anwendung erfordert so viele gleichzeitige Ausführungsthreads? Nur die am stärksten ausgelasteten Webserver empfangen sogar Tausende von gleichzeitigen Besuchern. Bewerbungen vom Typ Chef-Arbeiter / Job-Dispatcher, die ich geschrieben habe, geben immer weniger zurück, wenn die Anzahl der Threads / Prozesse viel größer ist als die Anzahl der physischen Kerne. Ich nehme an, es mag für numerische Anwendungen sinnvoll sein, aber in Wirklichkeit delegieren die meisten Leute Parallelität zu Bibliotheken von Drittanbietern, die in Fortran / C / C ++ geschrieben sind, nicht zu diesen Sprachen der neueren Generation.
quelle
Antworten:
Ein Anwendungsfall - Websockets:
Da Websockets im Vergleich zu einfachen Anforderungen langlebig sind, werden sich auf einem ausgelasteten Server im Laufe der Zeit viele Websockets ansammeln. Mikrothreads bieten eine gute konzeptionelle Modellierung und eine relativ einfache Implementierung.
Im Allgemeinen sollten Fälle, in denen zahlreiche mehr oder weniger autonome Einheiten auf bestimmte Ereignisse warten, gute Anwendungsfälle sein.
quelle
Es könnte hilfreich sein, über das nachzudenken, wofür Erlang ursprünglich entwickelt wurde, nämlich die Verwaltung der Telekommunikation. Aktivitäten wie Routing, Switching, Sensorsammlung / -aggregation usw.
Bringen Sie dies in die Web-Welt - betrachten Sie ein System wie Twitter . Das System würde beim Generieren von Webseiten wahrscheinlich keine Mikrothreads verwenden, aber es könnte sie beim Sammeln / Zwischenspeichern / Verteilen von Tweets verwenden.
Dieser Artikel könnte Ihnen weiterhelfen.
quelle
In einer Sprache, in der Sie keine Variablen ändern dürfen, erfordert das einfache Beibehalten des Status einen separaten Ausführungskontext (den die meisten Benutzer als Thread und Erlang als Prozess bezeichnen). Grundsätzlich ist alles ein Arbeiter.
Betrachten Sie diese Erlang-Funktion, die einen Zähler verwaltet:
In einer herkömmlichen OO-Sprache wie C ++ oder Java würden Sie dies erreichen, indem Sie eine Klasse mit einem privaten Klassenmitglied, öffentlichen Methoden zum Abrufen oder Ändern ihres Status und einem instanziierten Objekt für jeden Leistungsindikator haben. Erlang ersetzt den Begriff des instanziierten Objekts durch einen Prozess, den Begriff der Methoden mit Nachrichten und die Aufrechterhaltung des Status durch Tail-Aufrufe , die die Funktion mit den Werten neu starten, die den neuen Status ausmachen. Der verborgene Vorteil dieses Modells - und der größte Teil von Erlangs Daseinsberechtigung - besteht darin, dass die Sprache den Zugriff auf den Zählerwert mithilfe einer Nachrichtenwarteschlange automatisch serialisiert, sodass der gleichzeitige Code sehr einfach und mit einem hohen Maß an Sicherheit implementiert werden kann .
Sie sind wahrscheinlich daran gewöhnt, dass Kontextwechsel teuer sind, was aus Sicht des Host-Betriebssystems immer noch zutrifft. Die Erlang-Laufzeit ist selbst ein kleines Betriebssystem, das so optimiert ist, dass das Wechseln zwischen den eigenen Prozessen schnell und effizient vonstatten geht, während die Anzahl der Kontextwechsel, die das Betriebssystem durchführt, auf ein Minimum reduziert wird. Aus diesem Grund ist es kein Problem und wird empfohlen, viele tausend Prozesse durchzuführen.
quelle
counter/1
sollte einen Kleinbuchstaben verwenden. C;) Ich habe versucht, das Problem zu beheben, aber StackExchange mag keine 1-Zeichen-Änderungen.1) Die Tatsache, dass eine Sprache "skaliert", bedeutet, dass die Wahrscheinlichkeit geringer ist, dass Sie diese Sprache fallen lassen müssen, wenn die Dinge später komplexer werden. (Dies wird als "Gesamtprodukt" -Konzept bezeichnet.) Viele Leute werfen Apache aus genau diesem Grund für Nginx in den Sand. Wenn Sie sich der "harten Grenze" nähern, die der Thread-Overhead auferlegt, werden Sie ängstlich und überlegen, wie Sie daran vorbeikommen können. Websites können niemals vorhersagen, wie viel Datenverkehr sie erhalten werden. Daher ist es sinnvoll, ein wenig Zeit darauf zu verwenden, die Dinge skalierbar zu machen.
2) Eine Goroutine pro Anfrage nur zu Beginn. Es gibt viele Gründe, Goroutinen intern zu verwenden.
Die Leistung ist nicht der einzige Grund, ein Programm in CSP aufzulösen . Es kann das Programm tatsächlich verständlicher machen und einige Probleme können mit viel weniger Code gelöst werden.
Wie in den oben verlinkten Folien ist die gleichzeitige Verwendung von Code eine Möglichkeit, das Problem zu organisieren. Das Fehlen von Goroutinen entspricht dem Fehlen einer Karten-, Diktier- oder Hash-Datenstruktur in Ihrer Sprache. Sie können ohne auskommen. Aber sobald Sie es haben, können Sie es überall verwenden, und es vereinfacht Ihr Programm wirklich.
In der Vergangenheit bedeutete dies "Roll your own" Multithread-Programmierung. Aber das war komplex und gefährlich - es gibt immer noch nicht viele Tools, mit denen Sie sicherstellen können, dass Sie keine Rennen veranstalten. Und wie verhindern Sie, dass ein zukünftiger Betreuer einen Fehler macht? Wenn Sie sich große / komplexe Programme ansehen, werden Sie feststellen, dass sie eine Menge Ressourcen in diese Richtung verbrauchen .
Da Parallelität in den meisten Sprachen kein erstklassiger Bestandteil ist, haben die heutigen Programmierer einen blinden Fleck, warum sie für sie nützlich sein sollten. Dies wird erst deutlicher, wenn jedes Telefon und jede Armbanduhr auf 1000 Kerne zusteuert. Gehen Sie mit einem eingebauten Race-Detector-Tool auf Schiff.
quelle
Für Erlang ist es üblich, einen Prozess pro Verbindung oder andere Aufgabe zu haben. So kann beispielsweise ein Streaming-Audioserver einen Prozess pro verbundenem Benutzer haben.
Die Erlang VM ist für die Verarbeitung von Tausenden oder sogar Hunderttausenden von Prozessen optimiert, indem Kontextwechsel sehr kostengünstig vorgenommen werden.
quelle
Bequemlichkeit. Als ich anfing, Multithread-Programmierung zu machen, habe ich zum Spaß nebenbei eine Menge Simulationen und Spieleentwicklungen durchgeführt. Ich fand es sehr praktisch, einfach einen Thread für jedes einzelne Objekt abzuspinnen und es seine eigene Sache machen zu lassen, anstatt jeden einzelnen durch eine Schleife zu verarbeiten. Wenn Ihr Code nicht durch nicht deterministisches Verhalten gestört wird und Sie keine Kollisionen haben, kann dies die Codierung erleichtern. Mit der uns jetzt zur Verfügung stehenden Energie kann ich mir leicht vorstellen, ein paar tausend Threads abzuspulen, da ich genug Rechenleistung und Speicher habe, um mit so vielen diskreten Objekten umzugehen!
quelle
Ein einfaches Beispiel für Erlang, das für die Kommunikation konzipiert wurde: die Übertragung von Netzwerkpaketen. Wenn Sie eine http-Anforderung ausführen, verfügen Sie möglicherweise über Tausende von TCP / IP-Paketen. Fügen Sie dies hinzu, dass alle gleichzeitig eine Verbindung herstellen und Sie Ihren Anwendungsfall haben.
Betrachten Sie viele Anwendungen, die von großen Unternehmen intern verwendet werden, um ihre Aufträge zu bearbeiten oder was auch immer sie benötigen. Webserver sind nicht das einzige, was Threads benötigt.
quelle
Hier fallen Ihnen einige Rendering-Aufgaben ein. Wenn Sie eine lange Reihe von Operationen auf jedem Pixel eines Bildes ausführen und diese Operationen parallelisierbar sind, dann befindet sich sogar ein relativ kleines 1024x768-Bild in der Klammer "Hunderttausende".
quelle