Implizite Parallelität ^ kann viele Programmierer stark entlasten und sie auf den Computer stellen. Also ... warum ist es derzeit nicht weiter verbreitet?
^ Implizite Parallelität bedeutet, dass ein Computer in der Lage ist, mehr als eine Aufgabe gleichzeitig zu lösen, anstatt dass ein Programmierer diese Aufgabe mit Hilfe von Threads und dergleichen erledigen muss
concurrency
parallelism
Abbafei
quelle
quelle
Antworten:
Denn mit ein paar Ausnahmen (Haskell) gibt es keine Möglichkeit, dass der Compiler eine Schleife auspacken kann. Das Problem ist, dass jede Iteration durch die Schleife den globalen Status ändern kann. Wenn Sie dies in einer anderen Reihenfolge tun, kann dies zum Bruch führen. In haskell können Sie sich darauf verlassen, dass eine Funktion rein ist. Das heißt, sie liest oder ändert den globalen Status nicht und kann in beliebiger Reihenfolge ausgeführt werden.
Das eigentliche Problem ist, dass es mit wenigen Ausnahmen immer noch ein offenes Problem ist, wie man Parallelität gut macht. Die Gemeinden Erlang und Haskell scheinen sich recht gut zu entwickeln, aber es ist noch ein langer Weg, bis wir wirklich verstehen, wie man ein N-Core-System für große N programmiert.
quelle
Die meisten Programmiersprachen, die wir jetzt verwenden, kamen zu einer Zeit, in der Single-Thread-Programmierung und Einzelbenutzerinteraktion für viele Anwendungen am häufigsten verwendet werden (z. B. eigenständige Desktopanwendungen). Mit der Zunahme von Webanwendungen, Cloud Computing und Mehrbenutzeranwendungen benötigen wir jetzt mehr Anwendungen mit mehreren Threads.
Die älteren Programmiersprachen versuchen, Multi-Thread-Funktionen langsam von der Sprache selbst zu unterstützen (wie das Java, das java.util.concurrent hinzugefügt hat).
Neue Sprachen, die in Zukunft verfügbar sein werden, bieten eine bessere Unterstützung für Build-Threading und Parallelität.
quelle
Abgesehen von den in den anderen Antworten genannten Punkten (schwer zu beweisen, dass Operationen unabhängig sind und Programmierer seriell denken), muss ein dritter Faktor berücksichtigt werden: die Kosten für die Parallelisierung.
Die Wahrheit ist, dass Thread-Parallelität mit sehr erheblichen Kosten verbunden ist:
Thread-Erstellung ist sehr teuer: Für den Kernel ist das Starten eines Threads ungefähr das gleiche wie das Starten eines Prozesses. Ich bin mir nicht sicher über die genauen Kosten, aber ich glaube, dass sie in der Größenordnung von zehn Mikrosekunden liegen.
Thread-Kommunikation über Mutexe ist teuer: In der Regel erfordert dies einen Systemaufruf auf jeder Seite, wobei möglicherweise ein Thread in den Ruhezustand versetzt und wieder aktiviert wird. Dies führt zu Latenz sowie zu Cold Caches und gelöschten TLBs. Im Durchschnitt kostet das Aufnehmen und Freigeben eines Mutex ungefähr eine Mikrosekunde.
So weit, ist es gut. Warum ist dies ein Problem für die implizite Parallelität? Weil implizite Parallelität am einfachsten im Kleinen zu beweisen ist. Es ist eine Sache zu beweisen, dass zwei Iterationen einer einfachen Schleife unabhängig voneinander sind, es ist eine ganz andere Sache zu beweisen, dass das Drucken von etwas
stdout
und das Senden einer Abfrage an eine Datenbank unabhängig voneinander sind und parallel ausgeführt werden können ( Der Datenbankprozess könnte sich auf der anderen Seite der Pipe befinden!).Das heißt, die implizite Parallelität, die ein Computerprogramm nachweisen kann, ist wahrscheinlich nicht ausnutzbar, da die Kosten für die Parallelisierung höher sind als der Vorteil der Parallelverarbeitung. Andererseits ist die große Parallelität, die eine Anwendung wirklich beschleunigen kann, für einen Compiler nicht nachweisbar. Stellen Sie sich vor, wie viel Arbeit eine CPU in einer Mikrosekunde leisten kann. Wenn nun die Parallelisierung schneller sein soll als das serielle Programm, muss das parallele Programm in der Lage sein, alle CPUs für mehrere Mikrosekunden zwischen zwei Mutex-Aufrufen beschäftigt zu halten. Das erfordert eine wirklich grobkörnige Parallelität, die sich kaum automatisch beweisen lässt.
Schließlich keine Regel ohne Ausnahme: Die Ausnutzung impliziter Parallelität funktioniert dort, wo keine Threads beteiligt sind, was bei der Vektorisierung des Codes der Fall ist (unter Verwendung von SIMD-Befehlssätzen wie AVX, Altivec usw.). Das funktioniert in der Tat am besten für die Parallelität im kleinen Maßstab, die relativ einfach zu beweisen ist.
quelle
Programmierer denken seriell, und aktuelle Sprachen unterstützen dieses Modell. Mit Ausnahme der Nebensprachen wie Haskell Erlang usw. sind Sprachen (ich verzichte auf das Adjektiv "modern") im Wesentlichen High-Level-Assembler, bei denen wir dem Computer immer noch mitteilen, was zu tun ist, wann und wie. Bis wir ein Echosystem haben, in dem wir dem Computer mitteilen, welches Ergebnis verfügbar sein soll, haben wir als Programmierer nicht die geistige Fähigkeit, die Multithreading-Fähigkeit voll auszuschöpfen.
dh es ist nicht natürlich ......
quelle
don't have the patience
ist eine genauere Einschätzung alsdon't have the mental capacity
wenn. Im Laufe meiner Karriere habe ich viel mehr faule Programmierer gesehen als dumme . Ich hatte jedoch das Glück, in meinem ersten Studienjahr neben prozeduralem und OO funktionales Programmieren und feinkörniges paralleles Programmieren gelernt zu haben. Ich vermute, dass viele Programmierer nicht so viel Glück hatten und ihre Gedankengänge daher geradlinig waren.Transaktionen müssen ACID sein, daher tendiert der Programmierer hauptsächlich dazu, an einen Thread zu denken.
Sprachen und Plattformen müssen den Programmierer so weit wie möglich vor Parallelität schützen
Parallelität ist nicht so einfach zu testen wie die Funktionalität selbst, daher neigen Programmierer dazu, neben diesen Problemen zu bleiben und auch nicht an die Behandlung von Parallelität zu denken, was ein Fehler ist
quelle