Warum Java vom Prinzip her schneller als C++?


  • Mod

    Xin schrieb:

    Dann nimmt man einen unwichtigen Programmierer aus dem Ende der Nahrungskette, gibt dem einen C64 (fast 1MHz auf 8Bit Prozessorbreite) und der frisst mit seiner "Höllenmaschine" beliebig viele Mega-Workstations.

    ...und das kann er nicht deshalb machen, weil er besonders gut C++ oder Assembler oder Java oder sonstwas kann, sondern weil er denken kann (...oder weil er aufgepasst hat, als es in der Uni beim Thema Rekursion/Iterative Verfahren das typische Fibonacci-Beispiel gab). Das ist also ein ganz wunderbares Beispiel dafür, dass die Programmiersprache bezüglich der Performance nicht so relevant wie der Programmierer ist. Die Wahl der Programmiersprache ändert nicht die zeitliche Komplexität der gewählten Algorithmen.



  • Gregor schrieb:

    Naja, wenn hier schon so ein Simpel-Beispiel dafür gebracht wird, wie einfach man unperformanten Code schreiben kann...

    [Code...Benchmark]

    Das C++ Kompilat braucht 37 Sekunden, das Javaprogramm 41. Das C++-Programm ist hier also etwa 10% schneller. ...hui, das bewegt die Welt und sollte in jedem Fall der entscheidende Faktor bei der Wahl der Programmiersprache sein, heh? 😃 Naja, glaube nicht. Aber um es mal auf den Punkt zu bringen: Hier ist Java offensichtlich nicht bedeutend langsamer.
    Also: Zeigt mal, wo Java lahm ist.

    Hmm... kann es sein, dass Du die letzten Seiten Postings gar nicht gelesen hast und Dein Posting daher voll am Thread vorbeigeht?
    Nur so ein Gedanke... kann auch sein, dass ich nicht bemerkt habe, auf welches Posting Du Dich beziehst.

    Aber... wenn Du unbedingt ein Benchmark diskutieren möchtest...
    Welches Deiner beiden Programme verbrauchte effektiv mehr Speicher, um das Ergebnis zu produzieren?

    Es ist unsinnig, mit Java gegen C/C++ anstänkern zu wollen, weil Java in diesen Disziplinen immer den kürzeren ziehen wird. Die Frage, wo Java langsamer ist, hast Du mit Deinem Benchmark selber belegt. 4 Sekunden zu ignorieren, bedeutet nicht, dass es gleich schnell ist. Insbesondere bedeutet es, dass Java nicht erste Wahl ist, wenn es um Resourcen geht, dein Dein Benchmark belegt ja, dass C++ schneller ist und damit in Deiner Fragestellung 1. Wahl.
    Das dann als Erfolg verkaufen ist dann doch eher amüsant.

    Wenn Du Java magst, was Dein gutes Recht ist, erfreue Dich an den Vorteilen der reichhaltigen Standardbibliotheken, die Dir als Java-Entwickler teilweise schnellere Ergebnisse liefern, aber versuch bitte niemanden zu überzeugen, dass Java bzgl. Resourcenverbrauch mit C/C++ mithalten könnte. Das wird immer nach hinten losgehen.

    10% kann den Unterschied machen, ob ich einen zusätzlichen Server kaufen muss oder nicht und alle Folgekosten dazu tragen muss, die nicht erforderlich wären, wenn das Programm 10% schneller laufen würde. Wenn der Mehrverbrauch an Speicher dazukommt, entscheidet sich das evtl. noch schneller gegen Java.
    Bei Aufgaben, die 10 Tage Rechenleistung fordern, sind 10% ein Tag. Das bedeutet hier, dass die vom Ergebnis abhängigen Arbeitnehmer einen Tag früher Ergebnisse haben und weiterarbeiten können. Die Rechenanlagen sind in der Regel auch nicht billig. Wenn die 10% mehr erledigen können, erzeugen die Rechner auch 10% mehr Ertrag. Wenn ein BWLer 10% mehr Ertrag hört, wird der Dir sagen, mit welcher Sprache Du ein echtes rechnerisches Programmierproblem zu lösen hast.

    Wenn Du also von Deinem privaten Interesse an Primzahlen mal wegrückst, wirst Du vielleicht erkennen, dass es nicht nur HeimPCs und Anwendungsprogrammierung gibt, wo "nur" ein Privatmensch etwas kostenlose Freizeit verliert, weil er 10% länger vor dem Computer warten muss und sich ja 'ne neue CPU kaufen kann. Kostet heute ja nix mehr.
    Angenommen jeder hätte einen Rechner, dann wären das hier rund 800 CPUs. An meinem Schreibtisch stehen 3 Rechner. Aber Kostet ja nix mehr.

    Als Privatmensch mache ich gelegentlich Bild- und Videobearbeitung. Da interessieren mich 10% auch als Privatmensch schon, entsprechend kaufe ich das Produkt, dass schneller rechnet.



  • du musst auch die auslastung usw... dazunehmen.. der benchmark zeigt nicht wirklich was... nochdazu steht auch nicht mit welchem compiler und wie optimiert wurde... das spiel ja alles eine rolle... würds ja selbst testen, aber hab keinen java compiler. Hast du java als exe compiliert oder ganz normal mit der virtual maschine laufen lassen?? denn man kann auch eine exe erzeugen (bei msj++ zum beispiel)..

    Zeig mir einen java compiler der frei ist und den ich verwenden kann und ich zeigt dir wie das ergebniss mit nem guten c++ compiler und den besten einstllungen aussieht... dann geh ich doch von mehr als 10% unterschied aus... unter umständen.

    Außerdem sagt ja niemand das du nicht java verwenden sollt und darfst. Nur probiert mit bitte nicht zu erklären dass java c++ überholt weil es Runtime-optimieren kann.. das ist BLÖDSINN.
    Warum hab ich ja schon erklärt...

    [edit]
    @Gregor:
    dein code für c++ ist fehlerhaft... muss noch schauen warum... aber er ist es.
    der code ist leider recht kompliziert (shifts) weiß ned wielange das dauern wird...

    [edit]
    naja war nicht fehler haft aber naja bisl viel am stack... hab das mal ausgelagert also heap...

    mfg Manuel



  • Oh das ist ja mal etwas interessantes ein vergleich zwischen Java und C++. Sowas habe ich ja noch nie gelesen.



  • JBeni schrieb:

    JBeni schrieb:

    Über die seltsam unflexible, problemverursachende, unangepasste Pseudo-Verwaltung von Speicher bei der JVM, möchte ich mich lieber ausschweigen...

    Warum? Reden ist Silber, Schweigen ist Gold?

    Das System ist IMHO der grösste Nachteil der JVM, deshalb schweige ich.

    Da stichel ich noch ein wenig... 😉
    Das wichtigste Merkmal von Java ist die JVM und die JVM ist der größte Nachteil von Java. Damit ist das wichtigste Merkmal von Java ein Nachteil, wenn ich das grade richtig verstehe!?

    Jein.
    Zum einen kann die VM den Code während der Laufzeit optimieren, was ohne nicht (es sei denn das OS spielt mit) oder nur schwer möglich wäre. Wieviel diese Optimierungen verglichen zum Overhead bringen, ist ein anderes Thema, verlässliche Statistiken kenne ich nicht.
    GC ist kein Argument für eine VM, er würde auch ohne funktionieren.
    Portierbarkeit: dass man sich beim Schreiben eines Programmes immer sicher sein kann, dass ein "int" 32 bit big endian ist, egal was man damit macht oder wo man ihn hinschreibt, empfinde ich als Vorteil.
    Die seltsame Speicherverwaltung ist kein prinzipielles Problem einer VM, sondern ein speziefisches Problem der JVM. Insofern kann sich da durchaus mal was ändern in Zukunft. Dass die JVM laufend verbessert wird, bemerkt man ja bei jedem Release.
    Die VM bietet Vor- und Nachteile (wär hätte das gedacht), nur welche wichtig und welche nicht so bedeutend sind, ist nicht klar. Da meine Programme auf vielen verschiedenen OS laufen müssen, teils solche die ich selbst nicht besitze, ist für mich die (einfache) Portierbarkeit des Codes sehr wichtig.

    JBeni schrieb:

    Stimmt. Aber wo ist das Problem - weigern sich Programmierer bzgl. GUI-Frameworks dazuzulernen?

    Hoffentlich nicht *g*. Aber man kann ein Framework nicht in einem Tag kennen lernen. Wenn dann Wochen auf kennen lernen + coden + debuggen + etc. draufgeht ist das nicht so dolle.

    Hmm.. wie sollte man sonst das Know-How steigern, dass die Firma anbieten kann?

    Es gibt ja auch noch anderes zu lernen. Neue Datenbanksysteme, neue Eingabegeräte, wie man GUIs besser benutzbar macht, und und und.... alles kann man nicht lernen, dann sollte man die Zeit nicht für etwas verschwenden das man einfacher haben könnte/gar nicht benötigte.

    JBeni schrieb:

    Java 1.6 hat GARANTIERT ein Schlüsselwort, um Klassen zu verschachteln...

    ...

    Ok, wir diskutieren auf verschiedenen Ebenen. Hab erst jetzt kapiert, wie du das meinst.

    Die Zeitverzögerung wird bei vielen Problemen nicht groß auffallen, aber es bleibt dabei, dass Java bei jedem Zugriff zwei zusätzliche Takte verbrät, was in Schleifen oder vielen derartigen Zugriffen innerhalb von Schleifen sich schon zu bemerkbaren Sekunden zusammenaddieren kann.

    Hm, 2 GHz / 2 = 1'000'000'000 Schleifendurchläufe für eine zusätzliche Sekunde. Hm, selbst eine leere Schleife benötigt schon ein Zeitchen um das durchzugehen (um die 15 Sekunden auf einem 600Mhz-er).
    Wenn du Lust hast kannst du das gerne weiter ausprobieren, aber aussagekräftig ist es nicht. Es lässt sich auch irgendwas finden, wo Java schneller als C++ ist, genauso nichtssagend.
    Aussagekräftiger wären da Tests die Geschwindigkeiten verschiedener komplexer Algorithmen messen.

    Da die meisten Programmierer aber nicht fähig sind, sehe ich häufig beim ersten hinschauen, die Fehler im Sourcecode.

    Das SchlagInDasGesichtGefühl? 😉

    b) es ist effizienter erst zu denken, dann zu programmieren. Selbst wenn man effizient Fehler findet, ist es ein tierischer Aufwand, den man sich in 90% der Fälle hätte sparen können, wenn man nicht einfach programmiert hätte nach dem Motto 'Wird schon passen'.

    Selbst mit viel Erfahrung kann man nicht fehlerfreien Code schreiben (auch wenn ich dir ohne weiteres ein Verhältnis wie 1 Fehler / 5000 Zeilen zutraue).

    JBeni schrieb:

    schreib' mir eine PM

    Funktioniert in diesem Forum nicht. 😕

    Wenn Du mir schreiben möchtest, wirst Du meine E-Mail-Adresse sicherlich rausfinden.
    Ansonsten: fnfpun@ngebcf.pbz
    Rot13 ist Dein Stichwort.

    Maaaaaaaaaan, es geht nicht darum dass ich dich nicht finde. Es geht darum, dass ich einen Fehler in deinem Post gefunden habe 🤡


  • Mod

    Manuelh87 schrieb:

    du musst auch die auslastung usw... dazunehmen.. der benchmark zeigt nicht wirklich was... nochdazu steht auch nicht mit welchem compiler und wie optimiert wurde... das spiel ja alles eine rolle... würds ja selbst testen, aber hab keinen java compiler. Hast du java als exe compiliert oder ganz normal mit der virtual maschine laufen lassen?? denn man kann auch eine exe erzeugen (bei msj++ zum beispiel)..

    Zeig mir einen java compiler der frei ist und den ich verwenden kann und ich zeigt dir wie das ergebniss mit nem guten c++ compiler und den besten einstllungen aussieht... dann geh ich doch von mehr als 10% unterschied aus... unter umständen.

    [...]

    [edit]
    @Gregor:
    dein code für c++ ist fehlerhaft... muss noch schauen warum... aber er ist es.
    der code ist leider recht kompliziert (shifts) weiß ned wielange das dauern wird...

    mfg Manuel

    AFAIK kommen einige C++ Compiler nicht mit dem großen Array zurecht. Dann müsstest du das auf dem Heap erzeugen. Ansonsten würde mich der Fehler sehr interessieren. 🙂 ...und zeig mal, was du aus dem Programm noch so rausholst.

    ...zu den genutzten Compilern, JVM:

    gregor@linux:~/JavaProjects/Test/TestPrime> g++ --version
    g++ (GCC) 3.3.5 20050117 (prerelease) (SUSE Linux)
    Copyright (C) 2003 Free Software Foundation, Inc.
    This is free software; see the source for copying conditions.  There is NO
    warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
    
    gregor@linux:~/JavaProjects/Test/TestPrime> /usr/java/jdk1.6.0/bin/java -version
    java version "1.6.0-rc"
    Java(TM) 2 Runtime Environment, Standard Edition (build 1.6.0-rc-b67)
    Java HotSpot(TM) Client VM (build 1.6.0-rc-b67, mixed mode, sharing)
    

    Ich weiß jetzt nicht, was du unter "frei" verstehst. Die JVM kannst du dir zumindest kostenlos ohne Registrierung und inklusive Quellcode runterladen. Du darfst den Quellcode nur nicht verändern und dann deinerseits irgendwo veröffentlichen:

    https://mustang.dev.java.net/

    ...naja, interessant, wie ihr so einen 10% Unterschied bewertet. Ich sehe das anders. Aber ich glaube nicht, dass wir uns da irgendwie einigen können. Also sollten wir das besser lassen. 😉 😃



  • hab ich ja schon klargestellt; war kein echter fehler... obwohl man normalerweise solche mengen nicht auf den stack haut...sondern eben am heap anlegt... aber glaube das könnte man einstellen;

    naja ab wieviel prozent bei dem gleichen algo würdst den meinen das der unterschied trastisch ist?

    mfg Manuel



  • java\1:resize_message schrieb:

    Oh das ist ja mal etwas interessantes ein vergleich zwischen Java und C++. Sowas habe ich ja noch nie gelesen.

    Vor allem solch kompetente Äußerungen von "Experten" wie Manuelh87 und SIDEX sind mal was ganz neues 🙄 😃 😃


  • Mod

    Manuelh87 schrieb:

    hab ich ja schon klargestellt; war kein echter fehler... obwohl man normalerweise solche mengen nicht auf den stack haut...sondern eben am heap anlegt... aber glaube das könnte man einstellen;

    naja ab wieviel prozent bei dem gleichen algo würdst den meinen das der unterschied trastisch ist?

    mfg Manuel

    Hmmm... Wenn man das Array auf den Heap legt, wird das C++ Programm übrigens noch ein bischen langsamer. ...so schwinden die Prozente dahin. 😃 ...ein "macht man nicht so" und schon ist man noch ein Stückchen näher am Java-Level dran. 😃

    ...hab die Obergrenze mal etwas erhöht.

    gregor@linux:~/JavaProjects/Test/TestPrime> ./TestPrime
    Zwischen 0 und 2000000000 liegen 98222287 Primzahlen.
    GesamtZeit : 82 Sekunden
    gregor@linux:~/JavaProjects/Test/TestPrime> /usr/java/jdk1.6.0/bin/java -Xmx384m TestPrime
    Zwischen 0 und 2000000000 liegen 98222287 Primzahlen.
    GesamtZeit : 86568 Millisekunden
    

    ...nur noch 5%. Naja, egal: Aus meiner Sicht ist es irrelevant, ob es 5% oder 10% sind. Ich halte es in beiden Fällen für nicht erwähnenswert und repräsentativ ist es natürlich auch nicht.

    Du willst wissen, welche Abweichung bei der Performance ich für relevant halten würde? Naja: Am Anfang war Java um einenFaktor 100 langsamer als C++. da wurde es komplett interpretiert und natürlich galt es da als lahm. Später war es um einen Faktor 10 langsamer und natürlich galt es da immer noch als lahm. Noch später war so ein Faktor 2-4 drin und da fängt es dann schon an, für viele Dinge interessant zu werden. Jetzt ist es fast an der Performance von C++ dran und da gibt es dann aus meiner Sicht kaum noch Anwendungen, für die ein derartiger Unterschied noch relevant ist. Es kommt natürlich immer auf die spezielle Anwendung an und wenn man ein Programm hat, das tagelang rechnen muss, dann wird so ein Unterschied relevant. Aber das betrifft nicht sooo viele Programme. Für viele Anwendungsgebiete ist ein Faktor von 2 bis 4 durchaus akzeptabel, aber ich würde einsehen, dass man in diesem Bereich durchaus sagt, dass einem das zu langsam ist. Wenn der Geschwindigkeitsunterschied auf einen Faktor unter 2 absinkt, kann dieser Aspekt für die meisten Anwendungsgebiete IMHO nicht mehr ausschlaggebend sein. Bei 10% geht so ein Unterschied doch völlig neben irgendwelchen suboptimalen Algorithmen oder so unter. Man darf ja auch nicht vergessen, dass die Menschen, die davor sitzen, nicht das letzte aus der Sprache herausholen. ...die in den beiden Programmen realisierte Version des Siebs des Erathostenes ist ja auch nicht unbedingt optimal. Ich hatte das auch schonmal mit entsprechendem Aufwand deutlich stärker optimiert und habe da dann auch noch mehr als 10% rausgeholt. ...eher 50% oder so. Ich erinnere mich da nicht mehr so genau dran.

    EDIT: Frag mal Optimizer! Vielleicht erinnert der sich noch besser daran. 😃

    @Optimizer: *SCNR* 😃 😃



  • ich fühle mich ja geehrt das du mich als Experte bezeichnest...

    das hab ich allerdings nie von mir behauptet, also: Aufforderung an alle: "Bessert mich bitte aus wo ich fehler gemacht habe!"

    Das soll jetzt kein Angriff sein... werd auch garantiert nichts dummes (also in meinem fall garnichts) darauf antworten.

    mfg Manuel


  • Mod

    java\1:resize_message schrieb:

    Oh das ist ja mal etwas interessantes ein vergleich zwischen Java und C++. Sowas habe ich ja noch nie gelesen.

    Oh, sorry, aber die anderen waren das letzte mal noch nicht da. Mir ist klar, dass es diesen Gesprächsverlauf schon diverse male hier gab. ...und ich nutze sogar die gleichen Benchmarks, die ich schonmal genutzt hatte.

    ...tja: Ich schreib halt wiederverwendbaren Code. 🕶 🤡



  • JBeni schrieb:

    JBeni schrieb:

    JBeni schrieb:

    Über die seltsam unflexible, problemverursachende, unangepasste Pseudo-Verwaltung von Speicher bei der JVM, möchte ich mich lieber ausschweigen...

    Warum? Reden ist Silber, Schweigen ist Gold?

    Das System ist IMHO der grösste Nachteil der JVM, deshalb schweige ich.

    Da stichel ich noch ein wenig... 😉
    Das wichtigste Merkmal von Java ist die JVM und die JVM ist der größte Nachteil von Java. Damit ist das wichtigste Merkmal von Java ein Nachteil, wenn ich das grade richtig verstehe!?

    Jein.

    Also nicht nein... :->

    JBeni schrieb:

    Zum einen kann die VM den Code während der Laufzeit optimieren, was ohne nicht (es sei denn das OS spielt mit) oder nur schwer möglich wäre. Wieviel diese Optimierungen verglichen zum Overhead bringen, ist ein anderes Thema, verlässliche Statistiken kenne ich nicht.

    Ich auch nicht. Da ich auch nicht so programmiere, kann ich den Vorteil grade nicht einschätzen, da zur Laufzeit selten Klassen austausche, die ich zur Compilezeit nicht dafür vorgesehen habe.

    JBeni schrieb:

    Portierbarkeit: dass man sich beim Schreiben eines Programmes immer sicher sein kann, dass ein "int" 32 bit big endian ist, egal was man damit macht oder wo man ihn hinschreibt, empfinde ich als Vorteil.

    Hehehe, Dir ist aber schon klar, dass eine Klasse 'bigEndian' im Aufwand etwa so kompliziert ist, wie ein Hallo World?

    Hier sehe ich den Vorteil also irgendwie quasi gar nicht. Insbesondere auf Prozessoren nicht, die LittleEndian arbeiten und bei jedem Schritt erstmal selber umrechnen müssen. Ein int ist quasi eine Black-Box, die einen Wert repräsentiert. Man bearbeitet die BlackBox mit Operatoren und ansonsten nix damit zu tun.
    Das Problem ist damit nicht das aktuelle System - das Problem tritt ja nur ernstzunehmenden auf, wenn Du zum Beispiel ein TIFF-Loader schreibst. Da weißt Du nämlich nicht, ob Du gleich Little oder Big Endian geliefert bekommst und musst genauso umbauen, wie in C.

    JBeni schrieb:

    Die seltsame Speicherverwaltung ist kein prinzipielles Problem einer VM, sondern ein speziefisches Problem der JVM.

    Wo wir ja schon festgestellt haben, dass ich die GNU-JVM nicht nutzen darf, weil sonst Eclipse abschmiert und Java ohne JVM irgendwie auch witzlos ist. Fehler bei Zeigern sind auch nicht das Problem der Sprache, sondern des Programmierers, aber ohne Programmierer ist die Sprache auch witzlos ^^
    Probleme der JVM sind also definitiv Probleme, die sich auf Java auswirken.

    JBeni schrieb:

    Da meine Programme auf vielen verschiedenen OS laufen müssen, teils solche die ich selbst nicht besitze, ist für mich die (einfache) Portierbarkeit des Codes sehr wichtig.

    Und hier geht ein unbestrittener Punkt an Dich.

    JBeni schrieb:

    Aber man kann ein Framework nicht in einem Tag kennen lernen. Wenn dann Wochen auf kennen lernen + coden + debuggen + etc. draufgeht ist das nicht so dolle.

    Hmm.. wie sollte man sonst das Know-How steigern, dass die Firma anbieten kann?[/quote]
    Es gibt ja auch noch anderes zu lernen. Neue Datenbanksysteme, neue Eingabegeräte, wie man GUIs besser benutzbar macht, und und und.... alles kann man nicht lernen, dann sollte man die Zeit nicht für etwas verschwenden das man einfacher haben könnte/gar nicht benötigte.[/quote]

    Dem kann ich kaum widersprechen und wie ich sagte, sind die Standardlibs eigentlich der Vorteil, den Java hat.
    Es ist bedauerlich, dass sich da für C/C++ immernoch keiner dran gesetzt hat, um so weitreichend mal was anzubieten.
    Stünde eine IBM hinter C++ und würde C++ pushen, wie Sun Java pusht und MS C# pusht, dann hätten wir wieder faire Verhältnisse und würde sich auf Qualitäten der Sprache beschränken können.

    JBeni schrieb:

    Hm, 2 GHz / 2 = 1'000'000'000 Schleifendurchläufe für eine zusätzliche Sekunde. Hm, selbst eine leere Schleife benötigt schon ein Zeitchen um das durchzugehen (um die 15 Sekunden auf einem 600Mhz-er).
    Wenn du Lust hast kannst du das gerne weiter ausprobieren, aber aussagekräftig ist es nicht. Es lässt sich auch irgendwas finden, wo Java schneller als C++ ist, genauso nichtssagend.
    Aussagekräftiger wären da Tests die Geschwindigkeiten verschiedener komplexer Algorithmen messen.

    Normal... aber da gibt es soviele Dinge, die die Aussage wieder verfälschen, von daher beschränke ich mich auf die tatsächlichen Features.
    C++ ist definitiv schneller. Es hat Nachteile in der Speicheralloziierung, die bei C++ über das OS (Syscall...) abgewickelt wird, wo Java sich aus dem Heap bedienen darf. Damit ist Java schneller fertig, weil es nach dem Alloziieren weiterarbeiten darf, während C++ unterbrochen wird, bzgl. Rechenzeit liegt C++ aber soweit ich weiß, weiter vorn. Das kann man notfalls mit einem MemoryPool umgehen, dann ist C++ wieder oben auf.

    Es bleibt Frage der Machbarkeit: Es ist nicht machbar, schneller als Assembler zu werden. C ist nah dran, C++ arbeitet sich an C ran und Java kann gut programmiertes C++ nicht erreichen.

    Da die meisten Programmierer aber nicht fähig sind, sehe ich häufig beim ersten hinschauen, die Fehler im Sourcecode.

    Das SchlagInDasGesichtGefühl? 😉

    JBeni schrieb:

    Selbst mit viel Erfahrung kann man nicht fehlerfreien Code schreiben (auch wenn ich dir ohne weiteres ein Verhältnis wie 1 Fehler / 5000 Zeilen zutraue).

    Danke, aber das wäre zuviel der Ehre. Es gibt genug, die besser als ich sind.

    JBeni schrieb:

    schreib' mir eine PM

    Funktioniert in diesem Forum nicht. 😕

    Wenn Du mir schreiben möchtest, wirst Du meine E-Mail-Adresse sicherlich rausfinden.
    Ansonsten: fnfpun@ngebcf.pbz
    Rot13 ist Dein Stichwort.

    Maaaaaaaaaan, es geht nicht darum dass ich dich nicht finde. Es geht darum, dass ich einen Fehler in deinem Post gefunden habe 🤡[/quote]

    <groschenaufheb> 😉



  • Xin schrieb:

    Als Privatmensch mache ich gelegentlich Bild- und Videobearbeitung. Da interessieren mich 10% auch als Privatmensch schon, entsprechend kaufe ich das Produkt, dass schneller rechnet.

    nur um darauf mal zurückzukommen 🙂
    warum ist dann gerade maya, ein java programm, eines der marktführenden programme für 3d modeling, animationing und rendering in der industrie 🤡
    ich weiß, das ist nicht vergleichbar mit gelegentlicher bild- und videoverarbeitung. aber nur mal so als beispiel.

    ps: vergurkter thread hier



  • Gregor schrieb:

    EDIT: Frag mal Optimizer! Vielleicht erinnert der sich noch besser daran. 😃

    @Optimizer: *SCNR* 😃 😃

    Das werd ich dir nie verzeihen. 😉



  • SideWinder schrieb:

    Ich habe mit 19 auch noch Prozessortakte gezählt. Schade, dass das heute keiner mehr macht.

    Ich dachte wenigstens an der FH versuchen sie das einem auszureden. Offenbar nicht, wir leben weiterhin in einer kleinkarierten Programmierwelt. Es geht nämlich gar nicht so sehr um das optimalste Ergebnis für einen kleinen Teil sondern um die Abbildung und Abstraktion eines Gesamtsystems am Computer.
    MfG SideWinder

    ich sehe das genauso.

    @manuel87 und @xin
    euch ist schon klar, dass um komplexität beherrschen zu können man immer auf höheren abstraktionen aufsetzen muss? ich meine, wetten dass ich in HW viel schnellere programme hinbekomme als ihr mit c++ oder gar asm? die frage ist nur wie lange würde ich und wie lange würdet ihr dafür brauchen. deshalb hat man immer abstraktionen geschafft:
    - transistoren
    - logische gatter
    - mikrocode
    - maschinencode
    - asm
    - betriebssystem
    - hochsprachen

    und aussagen wie, die programmierer hätten auch in ihren über 500.000 zeilen code takte zählen können um daraus die beste performance rauszukriegen ist einfach realitätsfremd. das mag bei einigen auf wenige zeilen beschränkten algorithmen funktionieren jedoch nicht bei komplexen systemen! da wären wir heute noch auf dem stand aus den 60er jahren...

    ich finde z.b. c++ eine geniale sprache, die einem viel freiheiten bietet. zudem kann man dort abstraktionen schaffen, die keine laufzeit kostet (z.b. mit templates). ich programmiere jedoch viel lieber in java, weil ich dort einfach geile bibliotheken und geile entwicklungsumgebungen habe. nichtsdesto trotz hole ich auch einen profiler raus und identifiziere die teile die viel laufzeit kosten. diese kann man dann optimieren.

    Gruß mathik



  • JBeni schrieb:

    Portierbarkeit: dass man sich beim Schreiben eines Programmes immer sicher sein kann, dass ein "int" 32 bit big endian ist, egal was man damit macht oder wo man ihn hinschreibt, empfinde ich als Vorteil.

    Hehehe, Dir ist aber schon klar, dass eine Klasse 'bigEndian' im Aufwand etwa so kompliziert ist, wie ein Hallo World?

    Hier sehe ich den Vorteil also irgendwie quasi gar nicht. Insbesondere auf Prozessoren nicht, die LittleEndian arbeiten und bei jedem Schritt erstmal selber umrechnen müssen. Ein int ist quasi eine Black-Box, die einen Wert repräsentiert. Man bearbeitet die BlackBox mit Operatoren und ansonsten nix damit zu tun.

    Ich unterstelle jetzt den Programmierern der JVM einfach mal, dass die JVM nicht unnötig Bytes von Ints rumdreht ;), der Geschwindigkeitsverlust also nicht vorhanden ist.
    Andererseits, wenns zu Bitoperationen kommt: es gibt nicht mal die Chance eines Problems.
    Wennns ums Datei lesen/schreiben geht: was man irgendwo geschrieben hat, kann man auch wieder lesen. Wenn man eine Datei nicht selbst geschrieben hat (oder bestimmte Hardware spezifische Formate einhalten muss), steht das ganze natürlich auf der Kippe.

    JBeni schrieb:

    Probleme der JVM sind also definitiv Probleme, die sich auf Java auswirken.

    Ohne Zweifel.

    Es ist bedauerlich, dass sich da für C/C++ immernoch keiner dran gesetzt hat, um so weitreichend mal was anzubieten.
    Stünde eine IBM hinter C++ und würde C++ pushen, wie Sun Java pusht und MS C# pusht, dann hätten wir wieder faire Verhältnisse und würde sich auf Qualitäten der Sprache beschränken können.

    Das Zusammengesuche von Libs, wenn man mal mehr als einen vector benötigt, stört mich schon bei C++.
    Andererseits ist die Java-Library langsam ziemlich überladen. SQL-Befehle in derselben Lib wie GUIs, ein Collectionframework mit seltsamen Klassenhierarchien, naja...
    Manchmal wünsche ich mir, da würde mal jemand mit dem Rotstift fett Klassen rauswerfen. Die Vielfalt wird durch eine alles erschlagende Standardlibrary auch nicht gefördert. Also 1/4-Punkt an das C++ Model.



  • mathik schrieb:

    SideWinder schrieb:

    Ich habe mit 19 auch noch Prozessortakte gezählt. Schade, dass das heute keiner mehr macht.

    Ich dachte wenigstens an der FH versuchen sie das einem auszureden. Offenbar nicht, wir leben weiterhin in einer kleinkarierten Programmierwelt. Es geht nämlich gar nicht so sehr um das optimalste Ergebnis für einen kleinen Teil sondern um die Abbildung und Abstraktion eines Gesamtsystems am Computer.

    ich sehe das genauso.

    @manuel87 und @xin
    euch ist schon klar, dass um komplexität beherrschen zu können man immer auf höheren abstraktionen aufsetzen muss?

    und aussagen wie, die programmierer hätten auch in ihren über 500.000 zeilen code takte zählen können um daraus die beste performance rauszukriegen ist einfach realitätsfremd.

    Es ist nicht nur realitätsfremd, vor allem ist es nicht die Aussage, die hier getroffen wurde.

    Es zu können halte ich für wichtig. Es im richtigen Moment anzuwenden halte ich für wichtig. Jedes "Hallo Welt" hochgradig zu optimieren ist Schwachsinn und bei aktuellen Entwicklungswerkzeugen nicht sinnvoll umsetzbar.
    Wer im Falle der Notwendigkeit, aber nicht zu weiß, wie man benötigte Takte reduzieren kann, hat leider verloren. Von daher ist die Benutzung eines Profilers genau das, was gefordert wird. Damit zeigst du ja eben, dass Du versuchst, auf Resourcen entsprechend Deinen Möglichkeiten zu achten.
    Das ist bei der Anwendungsprogrammierung natürlich in der Regel nicht notwendig, da der Computer eh zu 99% auf den Anwender wartet.

    ---------------------------------------------
    Kommen wir nun zu etwas völlig anderem:

    JBeni schrieb:

    Andererseits, wenns zu Bitoperationen kommt: es gibt nicht mal die Chance eines Problems.

    Wenn alles LittleEndian ist oder alles BigEndian, dann gibt es kein Problem.
    Probleme gibt es nur, wenn Daten von außerhalb reinkommen und dann spielt es keine Rolle, ob Java grundsätzlich BigEndian nimmt oder wie in C die Sache nicht festlegt.

    JBeni schrieb:

    Es ist bedauerlich, dass sich da für C/C++ immernoch keiner dran gesetzt hat, um so weitreichend mal was anzubieten.
    Stünde eine IBM hinter C++ und würde C++ pushen, wie Sun Java pusht und MS C# pusht, dann hätten wir wieder faire Verhältnisse und würde sich auf Qualitäten der Sprache beschränken können.

    Das Zusammengesuche von Libs, wenn man mal mehr als einen vector benötigt, stört mich schon bei C++.
    Andererseits ist die Java-Library langsam ziemlich überladen. SQL-Befehle in derselben Lib wie GUIs, ein Collectionframework mit seltsamen Klassenhierarchien, naja...
    Manchmal wünsche ich mir, da würde mal jemand mit dem Rotstift fett Klassen rauswerfen. Die Vielfalt wird durch eine alles erschlagende Standardlibrary auch nicht gefördert. Also 1/4-Punkt an das C++ Model.

    Ich finde, da verdient keiner 'nen Punkt. Schwierigere Verfügbarkeit ist nicht wirklich besser als überlandene Standards.
    Der Vorteil bei C ist lediglich, dass sich nur jemand hinsetzen müsste und einen Standard ausrufen.

    Wer Programme nach dem XXX-Standard schreibt, benutzt STL, GTK, folgende Datenbank Interfaces, blablabla. Muss ja nichtmals wichtig sein, aber wenn man hätte eine Anlaufstelle, wo man Informationen finden kann.
    Wie bei Java. Ich suche was, surfe bei Sun vorbei und finde, was ich suche - wenngleich manches auch schon unter veraltet läuft.


  • Mod

    Xin schrieb:

    Von daher ist die Benutzung eines Profilers genau das, was gefordert wird. Damit zeigst du ja eben, dass Du versuchst, auf Resourcen entsprechend Deinen Möglichkeiten zu achten.

    BTW: Für Java gibt es einige wirklich ausgezeichnete Profiler. Den da zum Beispiel:

    http://profiler.netbeans.org/screenshots.html

    😋



  • Gregor schrieb:

    Das C++ Kompilat braucht 37 Sekunden, das Javaprogramm 41. Das C++-Programm ist hier also etwa 10% schneller. ...hui, das bewegt die Welt und sollte in jedem Fall der entscheidende Faktor bei der Wahl der Programmiersprache sein, heh? 😃

    10% sind nicht schlimm. ich würde nicht nach java umsteigen, wenn es 10% schneller als c++ wäre.
    lieber c++ und vb.net.
    c++: zero abstraction overhead, ich kann einen primzahlensucher bauen, wo ich genau weiß, daß ich ihn in assembler nicht schneller bauen könnte.
    c++: ich kann durch geschicktes design enorm viele potenzielle fehler zu compilerfehlern machen, so daß sie nie beim kunden ankommen.
    vb.net: alles hat einen so sinnvollen und sprechenden namen, daß man nie überlegen muß, wie man seinen plan verwirklicht, die zeichen fliegen einfach so in den editor und kaum sind sie drin, kann man den kram sogar problemlos lesen.

    Naja, glaube nicht. Aber um es mal auf den Punkt zu bringen: Hier ist Java offensichtlich nicht bedeutend langsamer. Wo ist es das denn dann?

    also von anfang an hat c++ um 10% die nase vorn. und man kann, wenn man lust hat, dann noch ein wenig optimieren, was den abstand normalerweise vergrößert.

    vielleicht sowas:

    #include <iostream>
    #include <ctime>
    using namespace std;
    
    typedef unsigned int u32;
    typedef size_t Size;
    
    inline bool getBit(u32 x,int p){//TODO: asm.h benutzen
    	return (x>>p)&1;
    }
    inline void setBitTrue(u32* x,int pos){//TODO: asm.h benutzen
    	*x|=(1<<pos);
    }
    inline int findFirstBitFalse(u32 x){//TODO: asm.h benutzen
    	int result=0;
    	while((x&1)==1){
    		x>>=1;
    		++result;
    	}
    	return result;
    }
    
    class BitField{
    private:
    	u32 *data;
    	Size size;
    	BitField(const BitField &);
    	BitField &operator=(const BitField &);
    public:
       BitField(Size _size)
    		:size(_size){
    		Size wordCount=(size+31)/32;
    		data=new u32[wordCount+2];
    		data[wordCount]=0;//such-ende-marke
    		data[wordCount+1]=u32(-1);//such-ende-marke
    	}
    	~BitField(){
    		delete[] data;
    	}
    	void clearAll(){
    		Size wordCount=(size+31)/32;
    		for(Size i=0;i!=wordCount;++i)
    			data[i]=0;
    	}
    	void set(Size pos){
    		Size wordPos=pos/32;
    		Size bitPos=pos%32;
    		setBitTrue(&data[wordPos],bitPos);
    	}
    	bool get(Size pos){
    		Size wordPos=pos/32;
    		Size bitPos=pos%32;
            return getBit(data[wordPos],bitPos);
    	}
    	Size findFirstFalse(){
    		return findNextFalse(Size(-1));
    	}
    	Size findNextFalse(Size pos){
    		++pos;
    		Size wordPos=pos/32;
    		Size bitPos=pos%32;
    		u32 word=data[wordPos];
    		if(bitPos!=0)
    			word=(word>>bitPos) | (-1<<(32-bitPos));
            if(word==u32(-1)){
                do
                    word=data[++wordPos];
                while(word==u32(-1));
    			bitPos=0;
    		}
    		Size r=findFirstBitFalse(word)+bitPos+32*wordPos;
    		if(r>=size) 
    			r=Size(-1);
    		return r;
    	}
    };
    
    u32 const step[8]={4,2,4,2,4,6,2,6};
    u32 const prime[12]={2,3,5,7,11,13,17,19,23,29,31,37};
    
    class PrimeGeneratorA{
    private:
    	u32 pos;
    	int m;
    public:
        u32 findFirst(){
            m=-11;
            pos=37;
            return 2;
        }
        bool isPrime(u32 x){
            if(x%7==0) return false;
            if(x%11==0) return false;
            if(x%13==0) return false;
            if(x%17==0) return false;
            if(x%19==0) return false;
            if(x<19*19) return true;
            if(x%23==0) return false;
            if(x%29==0) return false;
            if(x%31==0) return false;
            if(x%37==0) return false;
            u32 pos=37;
            u32 m=0;
            do{
                if(x%pos==0)
                    return false;
                pos+=step[m];
                m=(m+1)&7;
            }while(pos*pos<=x);
            return true;
        }
    	u32 findNext(){
            if(m<0){
                ++m;
                return prime[11+m];
            }
            do{
                pos+=step[m];
                m=(m+1)&7;
            }while(!isPrime(pos));
            return pos;
    	}
    };
    
    template<typename POS>
    class PrimeGeneratorD{
    private:
    	static Size const SIZE=1<<17;//muss gerade sein
    	BitField field;
    	Size pos;
    	POS start;
    	void setStart(POS newStart){
    		start=newStart;
    		field.clearAll();
    		PrimeGeneratorA p;
    		p.findFirst();
    		for(POS t=p.findNext();t*t<start+2*SIZE;t=p.findNext()){
    			POS ss=start+1;//+1 nicht n©tig!?
    			Size s=(ss+t-1)%t+1;
    			s=t-s;
    			if(s%2!=0)
    				s+=t;
    			s=s/2;
    			while(start+2*s+1<=t)
    				s+=t;
    			while(s<SIZE){
    				field.set(s);
    				s+=t;
    			}
    		}
    		pos=field.findFirstFalse();
    	}
    public:
    	PrimeGeneratorD():
    		field(SIZE),
    		start(POS(-1)){
    	}
    	POS findNext(){
    		pos=field.findNextFalse(pos);
    		while(pos==Size(-1)){
    			POS newStart=start+2*SIZE;
    			if(newStart<start)
    				return POS(-1);
    			setStart(newStart);
    		}
    		return start+2*pos+1;
    	}
    	POS findFirst(POS newStart=0){
    		newStart=newStart&~1;
    		if(newStart!=start)
    			setStart(newStart);
    		else
    			pos=field.findFirstFalse();
    		if(newStart==0)
    			return 2;
    		return start+2*pos+1;
    	}
    };
    
    template<typename POS>
    class PrimeGenerator{
    private:
    	static Size const SIZE=1<<17;//muss gerade sein
    	BitField field;
    	Size pos;
    	POS start;
    	void setStart(POS newStart){
    		start=newStart;
    		field.clearAll();
    		PrimeGeneratorD<POS> p;
    		p.findFirst();
    		for(POS t=p.findNext();t*t<start+2*SIZE;t=p.findNext()){
    			POS ss=start+1;//+1 nicht n©tig!?
    			Size s=(ss+t-1)%t+1;
    			s=t-s;
    			if(s%2!=0)
    				s+=t;
    			s=s/2;
    			while(start+2*s+1<=t)
    				s+=t;
    			while(s<SIZE){
    				field.set(s);
    				s+=t;
    			}
    		}
    		pos=field.findFirstFalse();
    	}
    public:
    	PrimeGenerator():
    		field(SIZE),
    		start(POS(-1)){
    	}
    	POS findNext(){
    		pos=field.findNextFalse(pos);
    		while(pos==Size(-1)){
    			POS newStart=start+2*SIZE;
    			if(newStart<start)
    				return POS(-1);
    			setStart(newStart);
    		}
    		return start+2*pos+1;
    	}
    	POS findFirst(POS newStart=0){
    		newStart=newStart&~1;
    		if(newStart!=start)
    			setStart(newStart);
    		else
    			pos=field.findFirstFalse();
    		if(newStart==0)
    			return 2;
    		return start+2*pos+1;
    	}
    };
    
    int main(){
    	u32 const max=2000000000;
    	clock_t start=clock();
    	PrimeGenerator<u32> pg;
    	u32 c=0;
    	for(u32 i=pg.findFirst();i<max;i=pg.findNext())
    		++c;
    	double time=(clock()-start)/double(CLOCKS_PER_SEC);
    	cout<<"Zwischen 0 und "<<max<<" liegen "<<c<<" Primzahlen.\n";
    	cout<<"GesamtZeit : "<<time<<" Millisekunden \n";
    }
    

    dabei ist zu sagen, daß das auch nur ein sieb des eratosthenes ist. halt fensterweise, um in den cache zu passen, heutzutage ist das RAM ja so unglaublich langsam. und das große sieb wird von einem kleinen sieb versorgt; weil ich die alten daten vergesse, kann ich leider nicht auf's haupt-sieb zugreifen.
    miss das doch auch mal auf deinem rechner, bin gespannt. wenn mein code langsamer ist (was durchaus im rahmen des möglichen liegt, den hab ich anno domini 2000 gestrickt, da war ich noch furchtbar schlecht, und nu kann ich ihn nicht mehr verändern, weil er zu kompliziert ist), stelle ich bis zum forumstreffen auf meine homepage den satz, daß ich ein ungeschickter programmierer bin und daß java gut ist.

    java hat oft beim nutzlos-optimieren, was man kommerziell kaum tut, sondern nur für WPCs, oft die nase hinten, weil irgend ein detail, auf das es gerade ankommt, nicht sauschnell geht. obiger primzahlencode lebt von einer schnellen BitField. und die würde sich sicherlich über eine

    #pragma warning(disable:4035)//warning C4035: no return value
    inline u32 findFirstBitFalse(u32 data)
    {
    	__asm	mov		eax,dword ptr[data];
    	__asm	not		eax;
    	__asm	bsf		eax,eax;
    };
    #pragma warning(default:4035)
    

    ganz prächtig freuen. den mov optimiert der compiler nach dem inlinen übrigens weg und nimmt für not gleich das register, wo data drin lebt, so daß nur 2 maschinenbefehle übrigbleiben.

    Wenn die Leute hier andauernd sagen, wie lahm Java ist, dann sollten sie das ja auch belegen können.

    zum glück sage ich nicht dauernd, java sei lahm. java ist recht flott und theoretisch schneller als c++. es spricht ja nix dagegen, einen compilerschalter "mach keine arrayindex-prüfungen" einzubauen und auch nix gegen "ich bin der mächtige JIT-compiler, ich lese bei lokalen objekten erstmal alle möglichen ablaufpfade und schaue, ob das objekt in weniger lokale container gesteckt wird und wenn nicht, haue ich es einfach auf den stack statt in den freispeicher".
    zur zeit gibt es noch hier und da ein paar defizite. das erinnert mich an c++ mit cout und c mit printf. cout ist theoretisch schneller als printf aber faktisch nicht. eine sache, die mich täglich beim aufstehen traurig stimmt und sicherlich der hauptgrund dafür ist, daß ich nicht der glücklichste mensch auf der welt bin.



  • @volkard: Auf meinem Gentoo AMD64 3200 folgendes Ergbenis:

    C++ Gregor: 31 (Änderung: Array auf dem Heap erzeugt, sonst erhalte ich einen Segmentation Fault)
    C++ Volkard: 5,42 👍
    Java Gregor: 33018 Millisekunden (client-vm)
    Java Gregor: 33016 Millisekunden (server-vm)

    Hast Du Literaturempfehlungen wo man diese Optimierungen nachlesen/verstehen/lernen kann, die Du gemacht hast? Darf auch ruhig englisch sein. 🙂


Anmelden zum Antworten