inline


  • Mod

    c++ler schrieb:

    Und wo ist da jetzt genau der Flaschenhals? Hast Du mal gemessen?

    Java selber ist der Flaschenhals
    Java sollte man immer nur als letzten Ausweg nehmen.
    Aber im richtigen Forum bist du ja immerhin schon. 😉

    Ach, Java ist inzwischen eigentlich schon ganz flott. 🙂 ...und wird immer besser und schneller. 🙂 Da kann man sich eigelich nicht beschweren, wenn man die Entwicklung der letzten Jahre betrachtet. Aber man muss halt, wie in jeder Sprache, wissen, wo die Schwachstellen in der Sprache oder der Standardbibliothek liegen, die man bei der Programmierung beachten sollte.


  • Mod

    in schrieb:

    nutze java 1.4 , da scheints den noch nicht zu geben :(.

    Bist Du an Java 1.4 gebunden? Wenn nein, empfehle ich Dir in jedem Fall, auf eine aktuelle Javaversion umzusteigen. mit neueren Versionen kommen ja auch immer Verbesserung bezüglich der Performance der Standardbibliothek und der JVM im Allgemeinen. Wer weiß: Vielleicht beseitigt das alleine schon deinen Flaschenhals. ...ausprobieren macht klug. 🙂



  • Gregor schrieb:

    c++ler schrieb:

    Und wo ist da jetzt genau der Flaschenhals? Hast Du mal gemessen?

    Java selber ist der Flaschenhals
    Java sollte man immer nur als letzten Ausweg nehmen.
    Aber im richtigen Forum bist du ja immerhin schon. 😉

    Ach, Java ist inzwischen eigentlich schon ganz flott. 🙂 ...und wird immer besser und schneller. 🙂 Da kann man sich eigelich nicht beschweren, wenn man die Entwicklung der letzten Jahre betrachtet. Aber man muss halt, wie in jeder Sprache, wissen, wo die Schwachstellen in der Sprache oder der Standardbibliothek liegen, die man bei der Programmierung beachten sollte.

    Aber sind String (oder Array) -Operationen nicht gerade eine Schwachstelle von Java? Die String Klasse ist doch total lahmer Müll. Und wenn man den StringBuffer mit den einfachen C Char Array (strcat...) vergleicht ist er wahrscheinlich auch deutlich langsamer. Und die ständigen ArrayIndexOutOfBound überprüfungen machen das ganze ja auch nicht gerade schnell.


  • Mod

    rdgdfsgdf schrieb:

    Aber sind String (oder Array) -Operationen nicht gerade eine Schwachstelle von Java? Die String Klasse ist doch total lahmer Müll. Und wenn man den StringBuffer mit den einfachen C Char Array (strcat...) vergleicht ist er wahrscheinlich auch deutlich langsamer. Und die ständigen ArrayIndexOutOfBound überprüfungen machen das ganze ja auch nicht gerade schnell.

    Das ist eher kein Performanceproblem von Java. Die String-Klasse hat ihre Stärken und Schwächen. Um die Schwächen auszugleichen, gibt es StringBuffer oder auch StringBuilder. Wenn man mit Java programmiert, sollte man eigentlich recht schnell lernen, wo man das eine und wo man das andere einsetzt. Die String-Klasse ist halt immutable und nicht wie eine dynamische Datenstruktur aufgebaut. Das sollte man wissen.

    Die Bereichsprüfungen bei Arrays sind auch kein echtes Performanceproblem. Du kannst ja mal ein C++ Programm und ein Java Programm vergleichen, die beide sehr viele Arrayzugriffe machen. Dann wirst Du feststellen, dass da kein wirklich großer Unterschied besteht. Vielleicht ein paar Prozent, aber nichts, was man bei "echtem Code" spürbar merkt.

    Echte Performancebremsen sehen in Java anders aus. Zum Beispiel fehlen in der Standardbibliothek Containerklassen für primitive Datentypen. Da kommt man dann schonmal in die Versuchung, die Containerklassen für Objekte mittels der Wrapperklassen für primitive Datentypen zu missbrauchen. Das ist natürlich ein riesiger Overhead, der Zeit und Speicher kostet. ...oder ganz allgemein haben Objekte in Java einen Overhead von 8 Byte pro Objekt. Das ist in C++ so nicht gegeben. Aber man kann sich vorstellen, dass es dann nicht so gut ist, große Mengen, kleiner Objekte in Java zu erzeugen. (...und das hat auch nichts mit dem GC zu tun, der oft für Performenceprobleme verantwortlich gemacht wird, mir persönlich aber noch nie diesbezüglich negativ aufgefallen ist.)

    (BTW: Die 8 Byte Overhead pro Objekt haben durchaus eine gewisse Berechtigung. Das ermöglicht Dinge wie Reflection usw.)

    Naja, zumindest gibt es schon Eigenschaften von Java, die man kennen sollte, um performanten Code zu schreiben. Das sind aber eher nicht die Dinge, von denen man immer hört, wenn jemand sagt, dass Java unglaublich langsam sei.

    BTW: Du kannst unter Java auch ganz bequem mit char-Arrays arbeiten, wenn Du willst. Die Umwandlung von und zu Strings ist da ganz einfach.



  • in schrieb:

    das hilft mir wirklich weiter. ich bin nicht der super java crack, aber deine aussagen lassen auch keine besonderen kenntnisse spüren. ich hab geschrieben, das beim zusammenbau der xml struktur die meiste zeit flöten geht. dass das so sein würde, konnte ich auch schon vor der implementierung abschätzen. natürlich habe ich nachgemessen, wer genau wie schuldig ist. und hättest du meine posts richtig gelesen, hättest du das auch gemerkt.

    Wenn dir das alles im Vorfeld doch schon so richtig klar war, wie erklärt sich dann dieser Thread? Jetzt schaun wir nochmal an den Anfang zurück:

    in schrieb:

    Hallo zusammen,

    gibts in Java sowas wie inline bei C++? Also um den Methodenrumpf an die rufende Stelle reinzukopieren...

    Gruß, in

    Uiuiui. 😮
    Vielleicht hätte ich es netter ausdrücken sollen, das gebe ich schon zu. Aber dass du tatsächlich im Vorfeld über die tatsächlichen Probleme bescheid wusstest, konnte man bisher nicht so ganz erkennen, auch wenn du inzwischen der Sache schon näher kommst.

    und falls du noch n beispiel haben willst, wie ich mit einer hashmap elemente einer db verwalten möchte (wenn ich dafür von dir einen _nützlichen_ tipp erhalte), bittesehr:

    public HashMap next() throws SQLException{
                    HashMap erg=new HashMap();
    		if (!res.next())
    			return false;
    		int anz=resmeta.getColumnCount();
    		for( int i=1; i<=anz; i++ ){
    			erg.put(resmeta.getColumnName(i),res.getString(i));
    		}
    		return true;
    	}
    

    so hatte ich mir ne connect klasse geschrieben, mit der ich recht angenehm und wiederverwendbar datenbankverwaltung ermögliche. aber das war halt grottenlangsam.

    Sieht so aus, als würdest du Spaltennamen als Keys benutzen. Das skaliert recht schlecht bei vielen Elementen, O(n/k), k = Anzahl Spalten der Tabelle € O(n) bei der Suche. Nach Möglichkeit sollten Keys immer sehr unterschiedlich sein, viele unterschiedliche Spaltennamen wirst du nicht haben.

    Allerdings weiß ich gar nicht, wie und wie viel du jetzt hier suchst. Damit das optimieren hier etwas bringt, müsstest du erstmal sichergehen, dass die Methoden der Hashmap das langsame sind und dann den Code von den Stellen posten, an denen sie aufgerufen werden. Bis jetzt hast du nur gezeigt, wie du die Hashmap befüllst, aber mir ist noch nicht klar, wie du das dann verwendest. Am besten, du beschreibst mal das typische Szenario, in dem du die Datenstruktur verwendest und was sie dann schnell erledigen können muss, dann finden wir schon das beste heraus.



  • Ich sehe grad, die Hashmap wird nur lokal referenziert und es wird nie aus ihr gelesen. Wofür dient sie überhaupt?


  • Mod

    Gregor schrieb:

    Die Bereichsprüfungen bei Arrays sind auch kein echtes Performanceproblem. Du kannst ja mal ein C++ Programm und ein Java Programm vergleichen, die beide sehr viele Arrayzugriffe machen. Dann wirst Du feststellen, dass da kein wirklich großer Unterschied besteht. Vielleicht ein paar Prozent, aber nichts, was man bei "echtem Code" spürbar merkt.

    Ich muss mich korrigieren. Ich habe da gerade ein paar Testprogramme in dieser Art geschrieben und musste feststellen, dass die Unterschiede doch enorm sind. Allerdings nicht immer zu Ungunsten von Java. ...zur allgemeinen Provokation kommt hier mal ein Beispiel, wo Java bei mir deutlich besser abschneidet. 😉

    #include <iostream>
    
    int main()
    {
       const int size = 100000;
       int *array = new int[size](0);
       int a = 0;
       for (int j = 0 ; j < 5 ; ++j)
       {
          for (int i = 0 ; i < 2000000000 ; ++i)
          {
             array[i%size] += i;
          }
       }
       for (int i = 0 ; i < size ; ++i)
       {
          a += array[i];
       }
       delete[] array;
       std::cout << a << std:: endl;
    }
    

    vs.

    public class ArrayTest
    {
       public static void main(String[] args)
       {
          final int size = 100000;
          int[] array = new int[size];
          int a = 0;
          for (int j = 0 ; j < 5 ; ++j)
          {
             for (int i = 0 ; i < 2000000000 ; ++i)
             {
                array[i%size] += i;
             }
          }
          for (int i = 0 ; i < size ; ++i)
          {
             a += array[i];
          }
          System.out.println(a);
       }
    }
    

    Ergebnis:

    gregor@linux:~/C++Projects/ArrayTest> /usr/java/jdk1.6.0/bin/javac ArrayTest.java
    gregor@linux:~/C++Projects/ArrayTest> time /usr/java/jdk1.6.0/bin/java -server ArrayTest
    1608650240
    
    real    1m13.778s
    user    1m11.931s
    sys     0m0.196s
    gregor@linux:~/C++Projects/ArrayTest> g++ -O3 -o ArrayTest ArrayTest.cpp
    gregor@linux:~/C++Projects/ArrayTest> time ./ArrayTest
    1608650240
    
    real    1m55.157s
    user    1m54.321s
    sys     0m0.105s
    

    Keine Ahnung, an was das hier liegt. 😉



  • Eigentlich sollte ein gut (optimal) optimierender Compiler deinen kompletten Quellcode wegoptimieren können (also zur Compilezeit die ganzen Schleifen auflösen und ausrechnen und nur das cout Konstante / System.out Konstante übriglassen).. Von daher könnte das ganze eher auf ein "welcher compiler optimiert besser" vergleich rauslaufen 😉



  • public class ArrayTest {
    	 public static void main(String[] args) {
    		int size = Integer.parseInt(args[0]);
    		int num = Integer.parseInt(args[1]);
    		int num2 = Integer.parseInt(args[2]);
    		long start = System.currentTimeMillis();
    		int[] array = new int[size];
    		int a = 0;
    		for (int j = 0; j < num; ++j) {
    			for (int i = 0; i < num2; ++i) {
    				array[i % size] += array[(j*i)%size] + i;
    			}
    		}
    		for (int i = 0; i < size; ++i) {
    			a += array[i];
    		}
    		long time = System.currentTimeMillis() - start;
    		System.out.println(size+ " " + num + " " +num2 + " erg: "+ a + " time: " + time);
    	}
    }
    

    100000 500 300000 erg: -1896966358 time: 21938

    vs.

    int main(int argc, char **argv){
    
    	int size = atoi(argv[1]);
    	int num = atoi(argv[2]);
    	int num2 = atoi(argv[3]);
    
    	struct __timeb64 start;
    	struct __timeb64 end;
    
    	_ftime64( &start );
    
    	int* array = new int[size];
    	memset(array,0,size);
    	int a = 0;
    	for (int j = 0; j < num; ++j) {
    		for (int i = 0; i < num2; ++i) {
    			array[i % size] += array[(j*i)%size] + i;
    		}
    	}
    	for (int i = 0; i < size; ++i) {
    		a += array[i];
    	}
    
    	_ftime64( &end );
    
    	long time = (end.time - start.time) * 1000 + (end.millitm - start.millitm);
    	printf("%d %d %d erg: %d time: %d",size,num,num2,a, time);
    
    	getch();
    
    	return 0;
    }
    

    100000 500 300000 erg: -1896966358 time: 18375

    java -server funktioniert bei mir nicht.


  • Mod

    6458345 schrieb:

    java -server funktioniert bei mir nicht.

    Schade. Das kann nämlich einen enormen Unterschied machen. Man schaue sich zum Beispiel den Unterschied zwischen Client-VM und Server-VM da an:

    http://weblogs.java.net/blog/opinali/archive/2005/11/mustangs_hotspo_1.html

    ...und welche Javaversion und welchen C++ Compiler nutzt Du eigentlich? 🙂

    Naja, ist ja auch egal. Ich will das nicht unbedingt vertiefen. Letztendlich ist das hier alles ein bischen OT.



  • Und wenn man in C Pointer verwendet:

    int main(int argc, char **argv){
    
    	int size = atoi(argv[1]);
    	int num = atoi(argv[2]);
    	int num2 = atoi(argv[3]);
    
    	struct __timeb64 start;
    	struct __timeb64 end;
    
    	_ftime64( &start );
    
    	int* array = new int[size];
    	memset(array,0,size);
    	int *ptr = &array[0];
    	int a = 0;
    	int pos = 0;
    	for (int j = 0; j < num; ++j) {
    		for (int i = 0; i < num2; ++i) {
    			(*ptr) += i;
    			if(pos == size) {
    				pos = 0;
    				ptr = &array[0];
    			}
    		}
    	}
    	for (int i = 0; i < size; ++i) {
    		a += array[i];
    	}
    
    	_ftime64( &end );
    
    	long time = (end.time - start.time) * 1000 + (end.millitm - start.millitm);
    	printf("%d %d %d erg: %d time: %d",size,num,num2,a, time);
    
    	getch();
    
    	return 0;
    }
    

    100000 500 1000000 erg: -1706365568 time: 2406

    public class ArrayTest {
    	 public static void main(String[] args) {
    		int size = Integer.parseInt(args[0]);
    		int num = Integer.parseInt(args[1]);
    		int num2 = Integer.parseInt(args[2]);
    		long start = System.currentTimeMillis();
    		int[] array = new int[size];
    		int a = 0;
    		int pos = 0;
    		for (int j = 0; j < num; ++j) {
    			for (int i = 0; i < num2; ++i) {
    				array[pos++] += i;
    				if(pos == size) {
    					pos = 0;
    				}
    			}
    		}
    		for (int i = 0; i < size; ++i) {
    			a += array[i];
    		}
    		long time = System.currentTimeMillis() - start;
    		System.out.println(size+ " " + num + " " +num2 + " erg: "+ a + " time: " + time);
    	}
    }
    100000 500 1000000 erg: -1706365568 time: 5516
    


  • java version "1.5.0_06"
    Java(TM) 2 Runtime Environment, Standard Edition (build 1.5.0_06-b05)
    Java HotSpot(TM) Client VM (build 1.5.0_06-b05, mixed mode)

    Visual studio .NET 2003


  • Mod

    ach ja. Ich hatte das ja auch nicht erwähnt:

    gregor@linux:~> /usr/java/jdk1.6.0/bin/java -server -version
    java version "1.6.0-beta2"
    Java(TM) SE Runtime Environment (build 1.6.0-beta2-b78)
    Java HotSpot(TM) Server VM (build 1.6.0-beta2-b78, mixed mode)
    gregor@linux:~> 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.
    

    Der C++ Compiler ist bei mir also zugegebenermaßen nicht mehr so ganz neu. Ich weiß nicht, ob sich da inzwischen viel bezüglich der Performance getan hat. Aber Du hast ja auch nicht unbedingt die optimale VM für Java verwendet. 😉



  • Verwende Prepared Statements (info bei SUN oder Javadoc),
    ist unendlich viel schneller....


Anmelden zum Antworten