Fragen: JAVA (Geschwindigkeit), D()
-
knivil schrieb:
Fuer mich ist das kein Problem, ich schreibe meine Anwendung einfach anders. Ich schreibe Programme angepasst an die "Aufgabenstellung"/Spezifikation.
Cool, du kannst Daten sich in Luft auflösen lassen?
-
@volkard:
VirtualAlloc nimmt man, wenn man *selbst* einen Allocator (z.B. Heap) implementieren möchte. Aber sicher nicht wenn man schnell mal 200 Byte braucht, denn das wäre langsam und verschwenderisch Ende nie.Yu beachten ist, dass malloc/free fuer groessere Speicherbereiche optimiert sein sollten als new/delete.
Auf vielen Systemen ruft new einfach malloc auf. Ist auch vollkommen OK.
yum beispiel koennte ich wissen, und das ist gar nicht mal so unrealistisch, dass waehrend des programmlaufs NIE signifikant viel speicher freigegeben und freigelassen wird und dass nur ein thread eryeugt wird und dass kein objekt groesser als 64k eryeugt wird.
was machen wir? na, einen buddy-allokator, der bei bedarf vom bs speicher holt, aber nicht ans bs yurueckgibt, der erst bei bedarf defragmentiert und der keine critsects hat. speedup gegenueber normalem new/delete beim MSVC6 war faktor 70. natuerlich ist auch gegen aktuelle compiler ein speedup drin, weil das normale new/delete laufend defragmentieren und ans bs yurueckgeben MUSS. pech gehabt.Vergleich deinen Buddy-Allocator mal gegen tcmalloc. Würde mich interessieren, wer da schneller ist. > 60% der Zeit die der Windows XP Allocator (bzw. auch der MSVC Allocator) brauchen, kommt schonmal vom enter/leave der CRITICAL_SECTION. tcmalloc vermeidet beim überwiegenden Grossteil aller Aufrufe jegliche Synchronisation, da jeder Thread eigene kleine Freelists bekommt. Weiters gibt es getrennte Freelists für bestimmte kleine Grössen wie 2, 4, 8, 12, 16, 20, 24 ... Bytes. Das "Defragmentieren" dieser kleinen Stückchen ist auch so billig dass es nicht weiter ins Gewicht fällt. Uswusf.
Der einzige echte Nachteil dem man so einem Allocator nachsagen könnte, ist, dass er in vielen Fällen etwas mehr Speicher verbraucht als ein einfacher Heap. Und in seltenen Fällen deutlich mehr Speicher. Lässt sich natürlich auch in gewissen Grenzen steuern, aber je weniger Memory-Overhead man erlaubt, desto langsamer wird wieder alles werden.
Gerade wo wir langsam aber sicher in Richtung "alles 64" gehen ist das denke ich nicht so schlimm.
-
volkard schrieb:
ich habe gehoert, die java VM behaelt den speicher auch gerne mal eine kleine weile (hack/trick/optimierung) und gibt ihn nicht dem BS zurueck, und das ist eigentlich recht unfair in den kuenstlichen benchmarks.
Wieso sollte man Speicher jemals ans OS zurückgeben? OK, auf einigen Plattformen ist das vermutlich sogar sehr wichtig. Aber auf Windows/Linux/BSD/... ??? Das OS trimmt doch sowieso automatisch das Working-Set, da scher' ich mich doch nicht irgendwas zurückzugeben
-
hustbaer schrieb:
volkard schrieb:
ich habe gehoert, die java VM behaelt den speicher auch gerne mal eine kleine weile (hack/trick/optimierung) und gibt ihn nicht dem BS zurueck, und das ist eigentlich recht unfair in den kuenstlichen benchmarks.
Wieso sollte man Speicher jemals ans OS zurückgeben? OK, auf einigen Plattformen ist das vermutlich sogar sehr wichtig. Aber auf Windows/Linux/BSD/... ??? Das OS trimmt doch sowieso automatisch das Working-Set, da scher' ich mich doch nicht irgendwas zurückzugeben
Das dachten sich die Programmierer von Company of Heroes auch und ich als Leidtragender darf auf meinem 32Bit OS regelmäßig das Programm neustarten, weil es bei längeren Spielen so viel Müll ansammelt, dass es den maximal zulässigen Anwendungsspeicher von 3GB unter Windows überschreitet. Super weiter so
-
Frickler-Nicht-Möger schrieb:
hustbaer schrieb:
volkard schrieb:
ich habe gehoert, die java VM behaelt den speicher auch gerne mal eine kleine weile (hack/trick/optimierung) und gibt ihn nicht dem BS zurueck, und das ist eigentlich recht unfair in den kuenstlichen benchmarks.
Wieso sollte man Speicher jemals ans OS zurückgeben? OK, auf einigen Plattformen ist das vermutlich sogar sehr wichtig. Aber auf Windows/Linux/BSD/... ??? Das OS trimmt doch sowieso automatisch das Working-Set, da scher' ich mich doch nicht irgendwas zurückzugeben
Das dachten sich die Programmierer von Company of Heroes auch und ich als Leidtragender darf auf meinem 32Bit OS regelmäßig das Programm neustarten, weil es bei längeren Spielen so viel Müll ansammelt, dass es den maximal zulässigen Anwendungsspeicher von 3GB unter Windows überschreitet. Super weiter so
Gratuliere, du hast gerade einen total unsinnigen Vergleich gebastelt.
Ich rede ja nicht davon dass ein Programm den Speicher nicht "an sich selbst" zurückgibt, also auf Deutsch: einfach korrekt verwaltet. Ich meine nur ans OS muss ich auf normalen PCs den Speicher nicht wirklich zurückgeben.
-
rapso schrieb:
Schnellgeschwindigkeit schrieb:
rapso schrieb:
Schnellgeschwindigkeit schrieb:
rapso schrieb:
Schnellgeschwindigkeit schrieb:
volkard schrieb:
Kleine Speicherbereiche auf dem Heap anfordern
siehe "small object allocator" , zum beispiel in "modern c++ design" von alexandrescu.
natürlich kann man sich nen workaround bauen, aber standardmäßig ist es nicht gerade schnell.
Das ist eine optimierung, kein work around. Du ersetzt einen algorithmus durch einen besseren. bei java musst du work-arounds einbauen z.b. garnicht allokieren zur laufzeit (ueblich auf vielen handy/smartphones) oder eigene free/alloc listen, weil du garnicht optimieren kannst und bei den einfachsten dingen ploetzlich einen furtchbar langen GC einspringen siehst.... oder im schlimmsten fall garnichts davno weisst.
Das ist eine optimierung, kein work around.
:p
anderer meinung? work around ist fuer mich wenn man nicht ohne das auskommt worum man drum arbeitet, es also noch beibehalten muss. aber belehre mich des besseren
Sind natürlich beides workarounds, weil nicht das Problem da gelöst wird, wo es auftritt, sondern eine eigene Speicherverwaltung verwendet wird, um die standard Speicherverwaltung zu umgehen.
das problem tritt beim speicherverwalten auf, deswegen loest man es dort. klar koenntest du bei c++ auch pro klasse das new ueberladen, falls du einen dedizierten allokator haben willst, aber meistens ist es halt speichereffizienter einen einzigen globalen pool zu haben, statt viele kleine mit ihrem overhead, denn am ende allokierst du nunmal nur speicher und nicht objekte, die objekte werden nachtraeglich im speicherblock initialisiert.
von daher sehe ich das als loesung an der richtigen stelle, wobei, wenn es dir nicht gefaellt, du jede andere stelle bei c++ nehmen kannst.
aber fuer den fall dass ich dich nur nicht verstehe: wie sehe denn in diesem fall deine idealloesung aus fuer dich (wenn du alle moeglichkeiten haettest die eine sprache liefern kann)?Der Idealfall wäre, wenn man die Speicherverwaltung nicht ändern müsste. Wenn die standard Speicherverwaltung schnell genug wäre, bräuchte man dafür keinen Workaround schreiben.
-
knivil schrieb:
In Java kann man diese Optimierungen auch machen. Dort sind es dann aber wirklich Hacks, z.B. globale (statische) Arrays ... so sollte man nicht in Java programmieren.
das problem ist eher, dass du in java diese probleme nicht loesen kannst
Fuer mich ist das kein Problem, ich schreibe meine Anwendung einfach anders. Ich schreibe Programme angepasst an die "Aufgabenstellung"/Spezifikation.
das und wie schreibst du es nun, wenn du ein immer konstant stabiles verhalten vom programm brauchst, ohne dass der gc es unterbricht, ohne auf allokationen von objekten verschiedener typen zu verzichten?
Man kann nicht erwarten, dass eine C++ uebersetzt nach Java genauso performant ist. Man kann nicht erwarten, dass Java uebersetzt nach C++ genauso performant ist (obwohl die Chancen hier besser sind). Genauso wenig kann man erwarten, dass ein englisches Buch ins Deutsche mittels Tool automatisch uebersetzt genauso toll ist. Will man Wortwitz etc. erhalten, dann muss man sich anders ausdruecken. Nichts anderes.
das hat ja auch niemand erwartet. wir sprechen von faellen in denen man schon ein program hat und optimieren will, z.b. die speicherverwaltung.
-
Dravere schrieb:
Jester schrieb:
Dravere schrieb:
Das ist kein Hack, das ist kein hinbiegen, das ist nur ein Nutzen von Features.
Hast Du grad mal ein Beispiel für einen Hack, der nicht nur das Nutzen von Features beinhaltet?
Sicher, wenn zum Beispiel jemand Kompilerspezifische Eigenschaft für das Lösen eines Problems heranzieht. Dann nutzt er nicht die Features der Sprache, sondern geht irgendwelche Umwege über den Kompiler und seine Eigenschaften.
Ja, ich denke das zeigt ganz gut, dass "nutzt nur Features" kein gutes Ausschlußkriterium für "ein Hack sein" ist. Eine "Kompilerspezifische Eigenschaft" ist übrigens auch nur ein Feature, oder nicht? Offensichtlich kann man nicht an vorhandenen Features und deren Nutzung festmachen, was ein Hack ist oder nicht. Man kann auch in reinem C++ Konstruktionen bauen, die ich als Hack bezeichnen würde, obwohl sie nur "Features nutzen".
-
Wikipedia sagt
Unter einer Umgehungslösung (engl. Workaround), auch Notbehelf, versteht man die Umgehung eines bekannten Problems innerhalb eines technischen Systems durch eine Hilfskonstruktion. Es ist eine provisorische Lösung, die die eigentliche Fehlerursache nicht behebt, sondern seine Symptome beseitigt oder zumindest mildert, um so trotzdem sofort zu einem gewünschten Ergebnis zu gelangen. Ein Workaround schafft somit Zeit für eine tiefergehende Ursachenanalyse.
Das in C++ ist keine Umgehungslösung, weil es den Fehler direkt an der Quelle beseitigt: Der Allokationsalgorithmus ist zu langsam, also wird der Allokationsalgorithmus ausgetauscht.
Wikipedia sagt
Hack stammt aus dem Englischen (to hack, „zerhacken“) und bedeutet im Computer-Slang „schlampig programmiert“, wenn es auf Programmcode bezogen, oder auch „anspruchsvoll“, wenn es auf eine Problemstellung bezogen ist. Der Begriff wird in ähnlichen Zusammenhängen benutzt:
Im Quellcode eines Computerprogramms signalisiert das Wort „Hack“, dass die Programmierer sich bewusst waren, dass die gefundene Lösung für ein Problem noch nicht ausgereift bzw. vom Standpunkt der Softwaretechnik her befriedigend ist. Dies kann auch durch äußere Umstände erzwungen sein, wie etwa durch fehlende oder mangelhafte Schnittstellen.Die Lösung ist ausgereift und befriedigend => kein Hack.
Aber wie man es bezeichnet ist schon wieder nur Nomenklatur, also bitte.. lasst ihn es doch als Workaround bezeichnen, wenn er meint, Fakt ist jedoch, dass es eine behebbare Schwäche ist und der Aufwand verhältnismäßig geringer ist als bei Java. Aber um den Vergleich mit Java gings ja noch nichtmal, es ist keine nicht behebbare Performanceschwäche, Punkt.
-
Jester schrieb:
Eine "Kompilerspezifische Eigenschaft" ist übrigens auch nur ein Feature, oder nicht?
Aber kein Sprachfeature!
Jester schrieb:
Man kann auch in reinem C++ Konstruktionen bauen, die ich als Hack bezeichnen würde, obwohl sie nur "Features nutzen".
Aber dann nutzt man Features nicht dafür, wofür sie eigentlich gedacht waren. Bzw. vielleicht wenn man jedes einzelne völlig zusammenhanglos anschaut, aber es geht hier ja um das Ganze und nicht um einzelne Codezeilen. Auch ist es prägend, dass man dann schnell mal verschiedene Features verwendet, um etwas anderes zu simulieren, bzw. den Hack oder Workaround zu kreieren.
Ich wiederhole mich, aber die Möglichkeit Einfluss auf die Speicherverwaltung zu nehmen, ist in C++ ein einzelnes Feature, welches explizit dafür gedacht ist.
Grüssli
-
Es gibt keinen Optimalen Allokationsalgorithmus.
So, wie es auch keinen optimalen Kinofilm oder optimales Medikament geben kann.Wer natürlich mit Reader's Digest glücklich wird, für den gelten andere Regeln. Der kauft sich auch den Besten Virenscanner (laut Computerbild) und nimmt selbstverständlich nur die Beste Programmiersprache (laut Sun). hihi.
-
volkard schrieb:
Es gibt keinen Optimalen Allokationsalgorithmus.
Natürlich richtig. Es gibt aber einige, die für wirklich viele Anwendungen "sehr gut" sind. Wobei "sehr gut" hier als "nicht nennenswert langsamer als der beste (bekannte) andere Algorithmus für die Anwendung" zu verstehen ist.
Dumm ist bloss, dass viele C++ Implementierungen den Default-Allocator vom Betriebssystem verwenden, und der Default-Allocator von vielen Betriebssystemen einfach grottig schlecht ist.
-
hustbaer schrieb:
volkard schrieb:
Es gibt keinen Optimalen Allokationsalgorithmus.
Natürlich richtig. Es gibt aber einige, die für wirklich viele Anwendungen "sehr gut" sind. Wobei "sehr gut" hier als "nicht nennenswert langsamer als der beste (bekannte) andere Algorithmus für die Anwendung" zu verstehen ist.
Dumm ist bloss, dass viele C++ Implementierungen den Default-Allocator vom Betriebssystem verwenden, und der Default-Allocator von vielen Betriebssystemen einfach grottig schlecht ist.
Es soll auch Betriebssysteme geben die über mehrere verfügen.
-
So not true schrieb:
hustbaer schrieb:
volkard schrieb:
Es gibt keinen Optimalen Allokationsalgorithmus.
Natürlich richtig. Es gibt aber einige, die für wirklich viele Anwendungen "sehr gut" sind. Wobei "sehr gut" hier als "nicht nennenswert langsamer als der beste (bekannte) andere Algorithmus für die Anwendung" zu verstehen ist.
Dumm ist bloss, dass viele C++ Implementierungen den Default-Allocator vom Betriebssystem verwenden, und der Default-Allocator von vielen Betriebssystemen einfach grottig schlecht ist.
Es soll auch Betriebssysteme geben die über mehrere verfügen.
Und wo wiederspricht das meinem Statement? Wer lesen (und verstehen) kann, ist klar im Vorteil...
-
volkard schrieb:
Es gibt keinen Optimalen Allokationsalgorithmus.
Ja, weil ich keinen geschrieben hab.