Textindexierungs Algorhitmen
-
Hi
das convertieren eines byteArrays in einen String kostet erstam zeit.
Ohne Bufferd.... wird jede zeile einzeln von der Festplatte angefordert. kostet auch wieder zeit.gruss
-
Termite schrieb:
Hi
das convertieren eines byteArrays in einen String kostet erstam zeit.
Ohne Bufferd.... wird jede zeile einzeln von der Festplatte angefordert. kostet auch wieder zeit.gruss
Stichwort: Memory Mapped I/O
mfg
v R
-
Ok, ich versuche das jetzt mal komplett auszulagern, so dass ich kein RandomAccessFile mehr nutze und das hin und herkopieren zu unterlassen, ich meld mich dann im laufe des Tages nochmal
-
Termite schrieb:
\nP\n währe ja dann unter windows 0x13 0x10 0x50 0x13 0x10 für Unix/Linux und Appel siehts dann entsprechend anders aus 0x10 0x50 0x10 oder 0x13 0x50 0x13.
Gibts in Java keine Textstreams?
-
mein gedanke war die Strings einfach zu umgehen, und diereckt auf einem byte[] zu arbeiten. mit einer art switch case do while konstruction. jesesmal wenn ein String angelegt wird wird ein neues Object angelegt, was wieder zeit kostet.
// WINDOWS LOESUNG File file = new File( fileName ); BufferedReader in = new BufferedReader( new FileReader( file ) ); // Dateiinput int lineCount = 0; // zeilenzähler int pos = 0; // byte position int state = 0; // für die Statemachine int c = 0; // das zuletzt gelesene zeichen while ( ( c = in.read() ) != -1 ) // ggf optimierungs möglichkeit wenn wir auf einen // Array arbeiten, das ein anderer Thread einliest. { pos++; switch (state) { case 0 : if ( c == 0x13 ) state = 1; else state = 0; break; case 1 : if ( c == 0x10 ) { state = 2; lineCount++; } else state = 0; break; case 2 : if ( c == 0x44 ) state = 3; else state = 0; break; case 3 : if ( c == 0x13 ) state = 4; else state = 0; break; case 4 : if ( c == 0x10 ) { // Do something // jetzt haben wir eine zeile gefunden mit nur einem P gefunden lineCount++; System.out.println("Page gefunden L: " + lineCount + " pos " + pos ); state = 2; // es könnte ja direckt drunter noch ein P kommen ;) } else state = 0; break; } }
ich post eigentlich ungern fertigen Code. aber vileicht wirds dadurch verständlicher was ich mein.
gruss
-
Von Strings hab ich nichts gesagt. Heißt das also, in Java gibts Textstreams nur über Strings? OK dann fällt das offensichtlich flach.
-
also nachdem java ja bekanntermassen nicht so der hammer ist, wenn dauernd irgendwelche variablen erstellt gelöscht etc werden, würde die ganze datei auf einen haps in einen string (oder vergleichbares) hauen, und dann über diesen laufen. dann haste auch nicht nervige io zugriffe (die meines erachtens die monsterzeit bei dir ausmachen). wenn dir alles auf einmal etwas viel ist, dann lies doch immer 512 byte oder so, und laufe über die. afaik kannste mit java auch auf byte ebene runter gehn
-
Habe jetzt so ziemlich genau Shadow of Mine's Lösung übernommen und die Zeit auf weniger als 1 Sekunde (800 ms) für die 8 MB Datei runterbekommen.
Termites Lösung werde ich auch einmal einem Speedtest unterziehen sobald ich wirklich große Dateien zum testen kriege.
Danke euch, ihr habt mir den Tag gerettet
(Blöd wenn alle Java Programmierer hier im Betrieb auf der Cebit sind ;))
-
@Bashar: In Java gibt es an I/O wirklich alles, was man sich nur vorstellen kann. :p
Meinste sowas? Wenn nicht, dann bitte genauer spezifizieren (dass char != byte ist, weißt du ja sicher). http://java.sun.com/j2se/1.5.0/docs/api/java/io/InputStreamReader.htmlKorbinian schrieb:
also nachdem java ja bekanntermassen nicht so der hammer ist, wenn dauernd irgendwelche variablen erstellt gelöscht etc werden, würde die ganze datei auf einen haps in einen string (oder vergleichbares) hauen, und dann über diesen laufen. dann haste auch nicht nervige io zugriffe (die meines erachtens die monsterzeit bei dir ausmachen). wenn dir alles auf einmal etwas viel ist, dann lies doch immer 512 byte oder so, und laufe über die. afaik kannste mit java auch auf byte ebene runter gehn
Hmmmm was spricht denn dagegen, nen Stream ordentlich zu buffern und einfach alles nacheinander auszulesen? Wir brauchen ja nur sequentiellen Zugriff. Also etwa so:
[BufferedReader <= InputStreamReader] (oder auch nicht, wenn man direkt auf den bytes arbeiten will) <= BufferedInputStream <= FileInputStream
-
Hi nochmal.
Wollte mich nur mal kurz bedanken für die Hilfe eingangs. Die Indexierung läuft super und schafft 14000 in weniger als 7 Sekunden.
Ihr habt mir echt geholfen