C++ Multithreading-Unterstützung
-
Inspiriert durch http://www.c-plusplus.net/forum/viewtopic-var-t-is-269673-and-highlight-is-.html
Gibt es Erweiterungen/Libraries/angedachte Extensions um in C++ in Zukunft soetwas zu erlauben:
// Preconditions: str.length() == 8, str contains only '0's or '1's char convert (const std::string& str) { char c = 0; // Nobody cares for a specific order __possible_mt_loop for(int i = 0; i < 8; ++i) c += MULTIPLIERS[i] * (str[i] - '0'); return c; }Ob es in diesem Fall überhaupt Sinn macht für 8 Durchläufe mehrere Prozessoren in einen neuen Thread switchen zu lassen ist natürlich sehr fragwürdig. Mir geht es mehr um die theoretische Möglichkeit.
Bzw. erkennen heutige Compiler solche Fälle ohnehin und erzeugen wenn nötig einen MultiCore/MultiCPU-Code?
MfG SideWinder
-
Ist das nicht genau das was OpenMP tut, oder übersehe ich da eine Besonderheit? Dort kann man z.B. einfach per "#pragma omp parallel for" angeben das die for Schleife parallelisiert wird. Das braucht soweit ich weiß Compilerunterstützung, allerdings sollten zumindest VC und gcc das können.
Das soetwas automatisch erkannt und gemacht wird hab ich bisher nur vom Intel Compiler gehört, hab da aber praktisch keine Erfahrung.
-
Dieses OpenMP scheint ja sehr fancy zu sein. Warum hört man davon nicht mehr? Werde mir das bei Gelegenheit genauer ansehen

MfG SideWinder
-
SideWinder schrieb:
Inspiriert durch http://www.c-plusplus.net/forum/viewtopic-var-t-is-269673-and-highlight-is-.html
Gibt es Erweiterungen/Libraries/angedachte Extensions um in C++ in Zukunft soetwas zu erlauben:
// Preconditions: str.length() == 8, str contains only '0's or '1's char convert (const std::string& str) { char c = 0; // Nobody cares for a specific order omp_set_num_threads(4); #pragma omp parallel for for(int i = 0; i < 8; ++i) c += MULTIPLIERS[i] * (str[i] - '0'); return c; }OpenMP: Ist sehr einfach und wird von so gut wie jedem aktuellen Compiler unterstützt. Schau in Zeile 7. Wenn du keine gemeinsamen Variablen hast, dann ist es kein Problem.
Dann gibt es noch deutlich performantere aber schwieriger zu steuernde Thread Bibliotheken wie: MPI, Posix Threads, Win32
SideWinder schrieb:
Ob es in diesem Fall überhaupt Sinn macht für 8 Durchläufe mehrere Prozessoren in einen neuen Thread switchen zu lassen ist natürlich sehr fragwürdig. Mir geht es mehr um die theoretische Möglichkeit.
So viel langsamer wird es meistens dadurch nicht.
SideWinder schrieb:
Bzw. erkennen heutige Compiler solche Fälle ohnehin und erzeugen wenn nötig einen MultiCore/MultiCPU-Code?
MfG SideWinderWie eins oben drüber geschrieben. Meistens wird der Code bei wenigen Durchläufen nicht wesentlich langsamer, bei vielen durchläufen aber deutlich schneller.
-
SideWinder schrieb:
Dieses OpenMP scheint ja sehr fancy zu sein. Warum hört man davon nicht mehr? Werde mir das bei Gelegenheit genauer ansehen

MfG SideWinder
Für C++ (wenn man mit Objekten arbeitet) ist das nicht unbedingt geeignet, dafür hat Intel die Threading Building Blocks (TBB) als freie(?) Bibliothek entwickelt.
Lars
-
SideWinder schrieb:
Dieses OpenMP scheint ja sehr fancy zu sein. Warum hört man davon nicht mehr? Werde mir das bei Gelegenheit genauer ansehen

MfG SideWinder
Es wird wirklich nicht oft genannt, aber wir hatten OpenMP sogar in einer Vorlesung über Parallele Programmierung. Ich nehme mal an, dass es nicht soo geläufig ist, dass es halt doch nur sehr beschränkt einsetzbar ist (aber genau solche Fälle, wie du zeigst sind ideal dafür).
darkfate schrieb:
Dann gibt es noch deutlich performantere aber schwieriger zu steuernde Thread Bibliotheken wie: MPI, Posix Threads, Win32
Das ist imo unglücklich ausgedrückt. OpenMP ist wie auch MPI eher eine Abstraktion der Mechanismen, welche Win32/Posix Threads einem bieten. Man kann das also nicht wirklich vergleichen. OpenMP (wie auch MPI) ist halt eingeschränkter, als wenn man auf einem niedrigeren Level arbeitet, aber es bietet einem eine sehr einfache Möglichkeit sein Programm für mehrere Kerne lauffähig zu machen. Das sieht man in der Java Implementierung z.B recht gut. Dort wird einfach ein Programm über den OMP Direktiven enthaltenden Code laufen gelassen und der erzeugt dann ein völlig normales Java Programm mit den eingebauten Mechanismen (Threads, Barrier usw.).
-
Es ist manchmal gar nicht so leicht mit selbstgebastelten Lösungen an omp heranzukommen, da es mehr leistet, als die Schleifenanzahl durch Kernanzahl zu teilen und entsprechend viele Threads zu erzeugen.
Auf der anderen Seite gibt es Anwendungen, wo omp einfach nicht die Flexibilität bietet, wirklich effektive Lösungen zu schreiben.
Ich benutze OpenMP gerne in Simulationen wo extrem viele sehr kleine Tasks abgearbeitet werden,( hauptsächliche "for_each" Dinge ) und das Programm an sich schon komplex genug ist.
-
brotbernd schrieb:
Es ist manchmal gar nicht so leicht mit selbstgebastelten Lösungen an omp heranzukommen, da es mehr leistet, als die Schleifenanzahl durch Kernanzahl zu teilen und entsprechend viele Threads zu erzeugen.
Hmm... da habe ich eher andere Erfahrung. Ich bevorzuge Posix und unter Windows nur Win32 Threads. Die Win32 Threads sind einfach deutlich schneller in ihrem eigenen OS. Das einzige Problem ist, dass man im Schnitt doppelt so viel Code benötigt.
-
OpenMP ist wie auch MPI eher eine Abstraktion der Mechanismen, welche Win32/Posix Threads einem bieten.
Ich denke MPI sollte nicht in einen Topf mit Threads geworfen werden. Normale Threads wie sie auch OpenMP nutzt sind fuer shared memory Syteme. MPI eben nicht.
-
Um wirklich schnell zu sein, auch über 2 Kerne hinaus, muss man sehr trickreiche Sachen implementieren, wie z.B. work stealing. Das Ganze auch noch cache-freundlich zu gestalten ist nicht trivial. Noch komplizierter wird es, wenn bestimmte Aufgaben neue Aufgaben hervorrufen.
Nur in den einfachsten Fällen kann man schnell was mit threads direkt effizient umsetzen, wenn man vorhersehen kann dass jeder Task, z.B. Schleifeniteration, gleich lange dauert. Dann geht es natürlich nicht optimaler als einfach die Iterationen fair zu verteilen.
Ansonsten wird es schwer, die meisten Implementierungen von OpenMP zu übertreffen. OpenMP ist aber eigentlich ein sehr ungewöhnliches Konzept für C++ und reiht sich nicht schön in ein STL-lastiges Programm ein. Sachen wie die Intel TBB oder MS PPL sind viel näher am ganzen STL-style dran, deswegen würde ich dort zuerst schaun.
In Zukunft könnte auch Boost.Task interessant werden.
-
knivil schrieb:
OpenMP ist wie auch MPI eher eine Abstraktion der Mechanismen, welche Win32/Posix Threads einem bieten.
Ich denke MPI sollte nicht in einen Topf mit Threads geworfen werden. Normale Threads wie sie auch OpenMP nutzt sind fuer shared memory Syteme. MPI eben nicht.
Das wollte ich eigentlich damit sagen. Tut mir leid, wenn es nicht so rüberkam. Ich habe da aber tatsächlich nicht so an wirklich verteilte Systeme gedacht.
Ich meinte da halt einfach, dass das Abstraktionen sind, welche durch diese Services umgesetzt werden können. MPI geht da natürlich noch ein Stück weiter und lässt auch entfernte Computer miteinander arbeiten und benötigt daher noch mehr Services, damit das überhaupt geht, aber man kann es natürlich auch einfach lokal benutzen.
Aber eben man darf Threads gar nicht mit MPI/OpenMP vergleichen, aber da sind wir uns glaube ich einig.
