dumme fragen zu ... dateien?
-
RandomAccessFile kann schon performant sein, sogar performanter als irgendwelche BufferedReader bzw. BufferedInputStreams aber nur wenn du tatsächlich größere Blöcke am Stück liest bzw. schreibst. Mit größer ist sowas ab 500-1000 Byte Länge gemeint. Aber selbst wenn du nur kleinere Stücke lesen willst, kann RandomAccessFile die richtige Wahl sein, nämlich dann wenn du tatsächlich andauernd im File hin- und herspringen musst, das File zu groß ist um es einmal komplett in den Speicher zu laden und es eher unwahrscheinlich ist, dass du hinter einem Lesezugriff gleich als nächstes sofort nochmal weiterlesen willst.
Nur bei sequentiellen Zugriffen, bei denen du die ganze Datei jeweils Zeichen für Zeichen in einer Schleife nacheinander lesen willst haben die Buffered... Klassen erhebliche Performance Vorteile. Das liegt aber vor allem daran, dass die Methode zum Lesen einzelner Zeichen an den meisten Streams sehr ineffizent implementiert ist (geerbt von InputStream). Ein Buffering macht auch das Betreibssystem schon, das hast du also auch beim simplen FileInputStream oder beim RandomAccessFile immer mit dabei. Die Buffered... Klassen machen nix anderes als jeweils immer gleich größere Blöcke am Stück aus dem darunter liegenden FileInputStream in ein internes Array zu lesen und aus diesem dann die Leseanfragen zu beantworten. Wenn der intern gepufferte Block leer ist wird automatisch ein neuer gelesen. Im Prinzip ist das aber überflüssiger Overhead wenn du deine Daten sowieso in ein größeres Array einlesen willst. Die (Buffered-)Reader zwingen dir außerdem intern immer einen ByteToCharConverter auf, der sich je nach Betreibssystem bzw. eingestellter Benutzersprache ändert und dir damit potentiell deine Daten korrumpieren kann sobald ein Benutzer mal keinen westeuropäischen Zeichensatz (ISO 8859-1) eingestellt hat, dessen Zeichen "zufällig" mit den ersten 256 Zeichen von Unicode übereinstimmen. Deshalb solltest bei der Verwendung von Readern/Writern den Zeichensatz immer explizit angeben, es sei denn, du willt mal tatsächlich reine Textdaten aus dem beim Benutzer voreingestllten 8-Bit Zeichensatz nach Unicode convertiert haben, was selten wirklich sinnvoll ist. Speziell bei Binärdaten ist es am Besten auf die Reader/Writer ganz zu verzichteen und bei den Input- und OutputStreams zu bleiben, zumal die auch noch performater sind.
Wenn du wirklich Performancekritische Sachen mit Random Access Files machen willst eignen sich natürlich auch die diversen FileBuffer aus dem newio Package. Damit kannst du dann vor allem auch Memory Mapped Files verwenden. Der Zugriff ist zwar etwas umständlicher und nicht mehr so schön verkettbar wie mit den Streams aber die Performance kann sich damit nochmal deutlich steigern lassen, besonders wenn du auch noch abwechselnd in das gleiche File an verschiedenen Stellen schreiben und lesen willst (wie z.B. bei einer Datenbank-Implementierung).
Um wirklich ein Gefühl dafür zu bekommen musst aber mal ein bisschen mit den diversen Varianten rumspielen und selber messen wie perfromant es ist. Alle Varianten haben ihre Vor- und Nachteile und können je nach Anwendungsfall geeigneter oder ungeeigneter sein.
-
nochmals zu dem thema,
ich habe jetzt etwas mit allem herumgespielt und es zumindest geschafft einfache textdateien zu erzeugen.
Hier nun die Frage:Was ist der UNterschied zwischen
FileOutpuStream und FileWriter ?
-
shisha schrieb:
Was ist der UNterschied zwischen
FileOutpuStream und FileWriter ?Die OutputStream-Klassen schreiben Bits und Bytes in Rohform. Man kann sie beispielsweise auch verwenden, um eine Bitmap-Datei (bmp) oder andere Binärdateien zu generieren (sofern man den Aufbau kennt) - auch Textdateien fallen darunter.
Die Writer-Klassen hingegen sind spezialisiert auf das Schreiben von Textdaten und nehmen dir schonmal die Arbeit mit den vielen unterschiedlichen Zeichencodes ab (ISO-8859-1, UTF-8, usw.).
-
mal wieder bin ich auf etwas gestossen das mir etwas kopfzerbrechen bereitet und zwar:
datainputstreams
wo kann ich diese einordnen? wofür sind sie gedacht? <bevor ich sie schamlos missbrauche>
Interessant ist der Zusammenhang DataInputStream <-> FileInputStream <-> FileReader
Hintergrund ist:
ich möchte die verschiedenen Varianten der IO kennenlernen und vlt ein kleines Programm schreiben um mp3 auszulesen
-
lies lieber was mit nem einfacheren format als mp3 aus.
das einzige was bei mp3 noch halbwegs einfach auszulesen geht, ist ein evtl. vorhandener ID3V1 tag
(also das lesen von bytes aus mp3 files ist natürlich einfach - dann mit diesen bytes was sinnvolles anzufangen ist das schwierige)
-
ich möchte einen string in bytes umwandeln, eig sollte das doch per
string.getbytes() klappen,
ich möchte nun aber sicher gehn dass das erzeugte array eine exakte größe hatwie kann ich das erreichen?
es geht vor allem darum wenn ich einen zu kleinen string habe
-
warum willst du die größe des arrays überprüfen, und womit willst du die dann vergleichen :?
-
ich möchte an den mp3 tags herumspielen
und da ist die länge eines tags fest vorgegeben, also muss ich mich da anpassennebenbei:wie kann ich in eine textdatei einen zeilenumbruch schreiben?
out.write(10) klappt nicht
-
\n
-
ja das war nichzt meine schuld der editor von microsoft hat die leerzeichen einfach nicht angezeigt^^
aber das andere problem hab ich noch:
string in byte festgegebener größe zu verwandeln
-
ich hab jetz ein wenig herumgespielt und hier ist das was mir sorgen bereitet:
String s = "Ich du er sie es"; String small = "kleiner"; String result; byte[] b , tmp; //System.out.println(s.length()); try { tmp = small.getBytes("US-ASCII"); b = s.getBytes("US-ASCII"); System.out.println(b.length); b = small.getBytes("US-ASCII"); System.out.println(b.length); result = new String(b); System.out.println(result); result = new String(tmp); System.out.println(result); System.out.println(b); System.out.println(b.length); System.out.println(tmp); System.out.println(tmp.length); }
b und tmp beinhalten am Schluss den selben String und haben die selbe Länge.
Aber was ist mit dem Rest von String s in b ?
b und tmp unterscheiden sich anscheinend doch.ich kann leider nicht viel damit anfangen und bitte um aufklärung
-
nun bin ich vollends verwirrt:
package bt; import java.io.*; public class Bytes { public static void main(String[] args) { byte[] b1, b2; String big = "langerstring"; String small = "kleiner"; try { b1 = small.getBytes("US-ASCII"); b2 = small.getBytes("US-ASCII"); System.out.println(b1); System.out.println(b2); } catch(Exception e){} } }
führt zu:
[B@addbf1
[B@42e816wieso erzeugt das programm 2 verschiedene ausgaben?
ich nehme doch den selben string auf die selbe art und weise ran...
-
-
würdest du mir erklären was damit genau gemeint ist.
zwar kann ich das übersetzen aber ich verstehe es noch nicht so recht.getClass().getName() + '@' + Integer.toHexString(hashCode())
in beiden fällen habe ich doch die selbe klasse "byte"
das würde das [B@ erkären das ich als ausgabe erhalte
aber der hash-code sollte doch auch gleich sein?!Also ich bin wirklich schwer von begriff aber ich bräuchte des wirklich mal erklärt.
Meine idee: vielleicht spielt die speicheradresse eine rolle? die unterscheidet sich ja auf jeden fall.
-
Hallo,
shisha schrieb:
...vielleicht spielt die speicheradresse eine rolle? die unterscheidet sich ja auf jeden fall.
Das könnte sein, denn:
As much as is reasonably practical, the hashCode method defined by class Object does return distinct integers for distinct objects. (This is typically implemented by converting the internal address of the object into an integer, but this implementation technique is not required by the JavaTM programming language.)
Siehe http://java.sun.com/javase/6/docs/api/java/lang/Object.html#hashCode()
MfG,
Probe-Nutzer
-
ein kleines problem:
ich habe einen String "blabla"
den ich in eine randomaccessfile schreiben möchte:RandomAccessFile out = new RandomAccessFile("out.txt","rw");
out.writeChars("blabla");nun habe ich 2 probleme dabei:+
1. wenn ich den modus der datei in "w" ändere tut sich gar nichts, wieso auch immer.
2. in der dtaei stehen sonderbarerweise immer \0 zwischen allen zeichen, wenn ich writeUTF verwende habe ich zwar das nicht mehr, aber ein sonderzeichen am anfang, das ich nicht haben möchte
-
Hallo,
schon wieder Fragen, die sich allein durch die Doku beantworten lassen, die solltest du unbedingt auch nutzen:
1. "w" ist nicht erlaubt! Siehe http://java.sun.com/javase/6/docs/api/java/io/RandomAccessFile.html#RandomAccessFile(java.lang.String,%20java.lang.String)
2. das ist ok, denn es werden Unicode-Zeichen geschrieben: Siehe http://java.sun.com/javase/6/docs/api/java/io/RandomAccessFile.html#writeChar(int)
Warum's bei writeUTF auch etwas "komisch" ist, steht auch dort
MfG,
Probe-Nutzer
-
ich habe zumindest bei utf herausgefunden woran es liegt, was bei unicode zeichen so besonders ist verschließt sich im moment auch noch,
das ist aber nicht das problem an sich:
wie umgehe ich es?
ich finde keine funktion die mir einfach den string reinschreibt, bei normalen filewritern ging das eigentlich wenn ich mich recht erinnere, warum bei rafs nicht?
oder besser gefragt:
nicht wieso klappts nicht, sondern wie erreiche ich mein ziel?
-
weil mir kein anderer weg einfiel hab ich jetz die bytes geschrieben in der von mir gewünschten us-ascii formatierung, aber gehts nicht einfacher?
-
Wenn du unbedingt ASCII schreiben musst, und du willst bei RAFs bleiben, dann sind die ...Byte-Methoden geeignet. Ansonsten kannst du auch auf FileInputStream und FileOutputStream (das sind Byte-Streams) ausweichen.
MfG,
Probe-Nutzer