Delphi-PRAXiS
Seite 1 von 4  1 23     Letzte » 

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Programmieren allgemein (https://www.delphipraxis.net/40-programmieren-allgemein/)
-   -   Delphi vs Visual C++ (https://www.delphipraxis.net/190996-delphi-vs-visual-c.html)

BigAl 28. Nov 2016 09:26

Delphi vs Visual C++
 
Hallo zusammen,

mich beschäftigt hier ein Thema, welches ich eigentlich so nie erwartet hätte. Kurz zum Hintergrund:

Ich habe hier über mehrere Jahre ein recht umfangreiches Projekt mit Delphi entwickelt. Das Projekt besteht aus mehreren Teilprogrammen. Eines dieser Teilprogramme ist ein Gleichungslöser, welcher große Matrizen mit komplexen Zahlen (Double-Komplex) nach Gauss löst. Bei diesem Programm handelt es sich um eine Kommandozeilen-Applikation, welche die vorbereitete Matrix in den Speicher lädt (aktuelle Berechnung ca. 25.000 Unbekannte), den "Solver" durchläuft und die Ergebnisse dann zur Weiterverarbeitung speichert.

Das Programm benötigt mit Delphi deutlich mehr als eine Stunde. Dazu muss man sagen, dass es bereits extrem optimiert ist. Ich habe die Matrix-Zugriffe soweit als möglich optimiert (z.T. auf Assembler-Ebene) sowie die Algorithmus selbst solange umgestellt bis ich die beste Laufzeit hatte. Vieles arbeitet als inline um die Aufrufzeiten weiter zu optimieren. Alle Compilerschalter wurden auf Leistung eingestellt. Weiterhin wurde der Algorithmus soweit angepasst, dass er in einer Multi-Thread Umgebung läuft und die verfügbaren CPU-Kerne des Systems soweit als möglich ausnutzt. Das Testsystem besitzt zwei XEON-Prozessoren mit jeweils 10 Kernen. Jeder zusätzlich Kern bracht in der Vergangenheit eine Geschwindigkeitssteigerung.

Nun hatten wir die Idee die CUDA-Kerne der Grafikkarte zum Berechnen zu nutzen. Dafür habe ich das Programm nun in C++ (Visual Studio) noch einmal geschrieben. Hierbei habe ich dann festgestellt, dass ich bereits mit etwa 8 CPU-Kernen das volle Leistungspotential erreiche und die Applikation mehr als doppelt so schnell rechnet (Ergebnis liegt nach etwa 30 Minuten vor). Weiteres Forschen ergab dann, dass der Flaschenhals nun nicht mehr die CPU-Kerne sondern der Speicherzugriff ist (die Test-Matrix hat eine Größe von ca. 9 GB). Ich muss dazu sagen, dass die komplette Matrix für die Berechnung in den Speicher geladen wird (MMF). CUDA-Programmierung würde das Ganze nicht mehr beschleunigen, da die Speicherzugriffe nicht mehr so effizient wären...

Ich habe nun festgestellt, dass das C++-Programm wesentlich effizienter arbeitet. Schaue ich mir den erzeugten Assembler-Code an, so ist der in Delphi zwar kompakter, in C++ jedoch wesentlich besser auf Geschwindigkeit optimiert. Es werden z.B. mehr die verfügbaren CPU-Register eingesetzt.

Ich denke nun ernsthaft darüber nach auch andere rechenintensive Programmteile nach C++ zu portieren. Die Sprache an sich gefällt mir zwar lange nicht so gut wie mein geliebtes Delphi aber das Ergebnis ist schon beeindruckend.

Habt Ihr ähnliche Erfahrungen gemacht?
Warum optimiert der C++-Compiler um so vieles besser als der Delphi-Compiler? (die Einzelthread rechnet etwa vier bis fünf mal schneller)

Mich würden mal Eure Erfahrung zu dem Thema interessieren. Habt Ihr ähnliche gemacht?

Alex

Sherlock 28. Nov 2016 09:39

AW: Delphi vs Visual C++
 
Kurz gesagt, und auch wenn es grob klingt, nicht böse gemeint: was Du da entdeckt hast, ist allgemein bekannt. C/C++ erzeugt deutlich schnellere und kompaktere Binaries als Delphi. Aber Numbercrunching ist nicht Delphis Spezialgebiet. Da geht es hauptsächlich um die Entwicklung hübscher Anwendungen für Fat Clients.

Sherlock

TiGü 28. Nov 2016 09:47

AW: Delphi vs Visual C++
 
Hast du bei der Neuimplementierung auf gängige Bibliotheken gesetzt oder alles wieder von Hand implementiert? OpenCL? C++ AMP?

Kurz und schmerzlos: Der Delphi Compiler ist für derartige Anwendungen eben nicht optimiert und wird es wohl nicht werden.
Allein schon aus dem Umstand heraus, dass die Mannschaft hinter dem Visual C++-Compiler wohl um ein Vielfaches größer sein wird, als das zuständige Team bei Embarcadero.

BigAl 28. Nov 2016 09:51

AW: Delphi vs Visual C++
 
Zitat:

Zitat von Sherlock (Beitrag 1354807)
Kurz gesagt, und auch wenn es grob klingt, nicht böse gemeint: was Du da entdeckt hast, ist allgemein bekannt. C/C++ erzeugt deutlich schnellere und kompaktere Binaries als Delphi. Aber Numbercrunching ist nicht Delphis Spezialgebiet. Da geht es hauptsächlich um die Entwicklung hübscher Anwendungen für Fat Clients.

Sherlock

Wobei das mit den kompakteren Binaries relativ ist. Wenn ich bei C/C++ die zur Laufzeit benötigten DLLs berücksichtige ist der Unterschied nicht mehr so groß. Bei Delphi werden ja per default alle BPLs etc. direkt in die EXE eingebunden. Lagere ich diese aus, dann bleibt auch nicht mehr viel übrig...

Aber ich gebe Dir recht. Für Oberfläche / GUI und Datenbank würde ich immer Delphi so ziemlich allem anderen vorziehen (was kenne). Bei rechenintensiven Programmen werde ich künftig aber wohl eher C/C++ einsetzen. Ich denke auch schon darüber nach das ganze mal unter Linux zu testen. Da hatte ich in der Vergangenheit - speziell bei Zugriffszeiten auf den Speicher - auch schon interessante Ergebnisse erzielt. Allerdings wäre das ein etwas aufwändigerer Test, da die Windows Funktion für MMF usw. ja dann nicht mehr funktionieren und ich die Linux-Pendants einsetzen müsste. Sollte mich da erstmal intensiver mit der Speicherverwaltung von Linux beschäftigen...

Alex

BigAl 28. Nov 2016 09:56

AW: Delphi vs Visual C++
 
Zitat:

Zitat von TiGü (Beitrag 1354809)
Hast du bei der Neuimplementierung auf gängige Bibliotheken gesetzt oder alles wieder von Hand implementiert? OpenCL? C++ AMP?

Kurz und schmerzlos: Der Delphi Compiler ist für derartige Anwendungen eben nicht optimiert und wird es wohl nicht werden.
Allein schon aus dem Umstand heraus, dass die Mannschaft hinter dem Visual C++-Compiler wohl um ein Vielfaches größer sein wird, als das zuständige Team bei Embarcadero.

Das Rahmenprogramm ist recht rudimentär. Kommandozeile halt. Der größte Unterschied dürfte wohl die Bibliothek für komplexe Zahlen sein. Bei C++ habe ich den Standardtyp "complex" verwendet (complex<double>). In Delphi habe ich das selbst geschrieben usw. mir möglich optimiert. Wie gesagt: Bereits kleine Umstellen bei der Berechnung haben teilweise ein paar Nanosekunden gebracht, was sich am Ende gleich wieder in Minuten geäußert hat. Das Delphi-Programm brauchte ursprünglich etwa vier Stunden. Ich habe so lange optimiert bis es "nur noch" etwas mehr als eine Stunde benötigte... Im C++-Programm habe ich bis jetzt noch gar nichts optimiert...

Alex

TiGü 28. Nov 2016 10:03

AW: Delphi vs Visual C++
 
Mal als Einstieg zu C++ AMP, denn die Stunde kriegst du bestimmt noch kürzer hin:
https://msdn.microsoft.com/en-us/library/hh873134.aspx

Der schöne Günther 28. Nov 2016 10:07

AW: Delphi vs Visual C++
 
Ich habe eigentlich nichts neues beizutragen, außer dass ich auch dachte dass der Geschwindigkeitsunterschied nicht so überraschend sein sollte. Hatten wir hier vor ein, zwei Jahren nicht sogar mal ein Thema wo selbst JavaScript im Browser schneller Rechnungen gelöst hat als eine DCC32-Delphi-Anwendung und alle waren danach ganz depressiv? :cyclops:

Ich stecke da schon viel zu lange nicht mehr drin, aber bist du dir wirklich sicher dass man mit CUDA/OpenCL nicht doch mehr rausholen kann? Die blanke Rechenleistung ist ja teilweise gewaltig, mit dem Hoch/runterladen auf den Speicher ... keine Ahnung wie viel sich da in den letzten Jahren getan hat...

Assarbad 28. Nov 2016 10:19

AW: Delphi vs Visual C++
 
Zitat:

Zitat von BigAl (Beitrag 1354810)
Wobei das mit den kompakteren Binaries relativ ist. Wenn ich bei C/C++ die zur Laufzeit benötigten DLLs berücksichtige ist der Unterschied nicht mehr so groß. Bei Delphi werden ja per default alle BPLs etc. direkt in die EXE eingebunden. Lagere ich diese aus, dann bleibt auch nicht mehr viel übrig...

Eigentlich würde es sich gehören zu erwähnen welche Bibliotheken du meinst, denn bei C++ ist die Sache eben im Gegensatz zur VCL bei Delphi nicht eindeutig. Die VC++-Laufzeitbibliothek kann bei einem WTL-Programm bspw. mit eingelinkt werden und dann komme ich noch immer auf deutlich kleinere .exe-Dateien als mit Delphi. Selbst bei einem statisch gelinkten MFC-Programm gelingt dies oft. Nur wenn du sowas wie Qt oder wxWidgets einsetzt, wird der Overhead größer als bei Delphi.

Aber Größe ist ja nicht alles. Manchmal kann auch Assemblercode der länger ist schneller sein als jener der kürzer ist. Man denke nur an die Einzelfallbehandlung in memcpy/memmove um ausgerichtete DWORDs/QWORDs kopieren zu können statt einzelne Bytes.

Zitat:

Zitat von BigAl (Beitrag 1354810)
Allerdings wäre das ein etwas aufwändigerer Test, da die Windows Funktion für MMF usw. ja dann nicht mehr funktionieren und ich die Linux-Pendants einsetzen müsste. Sollte mich da erstmal intensiver mit der Speicherverwaltung von Linux beschäftigen...

Ist eher einfacher als auf Windows, finde ich.

mmap() ist eigentlich fast schon alles was du benötigst.

Wenn du auf C++ usw. setzt würde ich dir wärmstens empfehlen dich mit existierenden Bibliotheken ala SageMath oder Blitz++ usw. auseinanderzusetzen. Da existiert unter Umständen vieles schon und wurde oft von vielen Leuten bereits optimiert. Kann sein, daß du damit noch mehr rausholen kannst.

Zuguterletzt scheint sich bei dir dann auch der Einsatz eines Profilers zu rechnen. Auf Windows wären da AQTime (unterstützt übrigens auch Delphi) und vTune (kann auch Kerneltreiber analysieren). Auf Linux haste eine große Auswahl von gprof über oprof zu den exotischeren Vertretern. CacheGrind könnte auch Sinn machen, da es bei dir auch um kleinste Optimierungen geht.

Zitat:

Zitat von Der schöne Günther (Beitrag 1354815)
Ich habe eigentlich nichts neues beizutragen, außer dass ich auch dachte dass der Geschwindigkeitsunterschied nicht so überraschend sein sollte. Hatten wir hier vor ein, zwei Jahren nicht sogar mal ein Thema wo selbst JavaScript im Browser schneller Rechnungen gelöst hat als eine DCC32-Delphi-Anwendung und alle waren danach ganz depressiv? :cyclops:

Nicht verwunderlich, da die heutigen JavaScript-VMs viel vom Code in nativen Code für die Ziel-CPU übersetzen (begann vor einigen Jahren mit V8). Da muß man schon auf einer sehr exotischen Architektur unterwegs sein um von diesen Optimierungen nicht zu profitieren.

Und wenn man dann noch betrachtet, daß allein der Umstieg vom mitgelieferten Compiler von MSVC langsameren Code erzeugt als der entsprechende (kompatible) Intel-Compiler - zumindest für Intel-CPUs - weißte auch bescheid. Da ist noch viel Potential, allein aufgrund der Tatsache daß Compiler wie Delphi oder MSVC für allgemeine Anwendungsfälle statt spezielle CPU-Modelle optimieren.

Chemiker 28. Nov 2016 10:36

AW: Delphi vs Visual C++
 
Hallo,

ein interessanter Beitrag.

Ich würde auch noch die Anmerkung machen grade im Hinblick auf die Speicherzugriffe, ob es sich um 32- oder 64 –Bit Programme handelt.

Bis bald Chemiker

BigAl 28. Nov 2016 10:37

AW: Delphi vs Visual C++
 
Zitat:

Zitat von Der schöne Günther (Beitrag 1354815)
Ich habe eigentlich nichts neues beizutragen, außer dass ich auch dachte dass der Geschwindigkeitsunterschied nicht so überraschend sein sollte. Hatten wir hier vor ein, zwei Jahren nicht sogar mal ein Thema wo selbst JavaScript im Browser schneller Rechnungen gelöst hat als eine DCC32-Delphi-Anwendung und alle waren danach ganz depressiv? :cyclops:

Ich stecke da schon viel zu lange nicht mehr drin, aber bist du dir wirklich sicher dass man mit CUDA/OpenCL nicht doch mehr rausholen kann? Die blanke Rechenleistung ist ja teilweise gewaltig, mit dem Hoch/runterladen auf den Speicher ... keine Ahnung wie viel sich da in den letzten Jahren getan hat...

Hallo Günther,

bei CUDA sehe ich momentan das Problem mit dem Speicherzugriff. Natürlich ist der Speicher auf den Grafikkarten rasend schnell, allerdings muss erstmal das was berechnet wird dorthin kommen. Weiterhin kenne ich keine Grafikkarte, welche die gesamte Matrix aufnehmen könnte. Die besten Karten haben derzeit 4 GB. Wenn die Karte auf den Speicher des Host-Rechners zugreifen muss ist diese scheinbar langsamer als ein Zugriff durch den Hauptprozessor (so steht es zumindest in meinen CUDA-Büchern). Die GAUSS-Lösung benötigt halt anfangs den Zugriff auf die gesamte Matrix. Gegen Ende wird das zwar immer weniger, dann läuft es aber auch wesentlich schneller. Ich habe hier auch paar Artikel bezüglich paralleler Lösung durch Aufteilung in Untermatrizen, das übersteigt aber mein mathematisches Verständnis...

Alex


Alle Zeitangaben in WEZ +1. Es ist jetzt 14:36 Uhr.
Seite 1 von 4  1 23     Letzte » 

Powered by vBulletin® Copyright ©2000 - 2021, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2021 by Daniel R. Wolf