Advanced   Java   Services Grundlagen Back Next Up Home


Basisinformationen

Die meisten Klassen zur Dateibehandlung finden sich im Package java.io Es ist also für diese Klassen ein import java.io.*; notwendig. In diesem Package kann man die Klassen grob nach der Art unterscheiden, auf was für Dateien zugegriffen werden soll. Im folgenden eine kleine Übersicht über die Möglichkeiten, die das Package bietet.


Übersicht über das Package java.io

Des weiteren gibt es auch die Möglichkeit, auf gepackte Dateien zuzugreifen. Die entsprechenden Klassen finden sich in den Packages java.util.zip und java.util.jar. Mit Hilfe dieser Klassen kann man

Beispiele zum Zugriff auf zip- und gz-Dateien finden sich in  Lesen und Schreiben von .zip-Dateien,  sowie in  Lesen und Schreiben von .gz-Dateien.


Grundlegende Vorgänge

Ein Dateizugriff besteht im Normalfall aus drei zusammenhängenden Teilen:

In Java wird das Öffnen einer Datei durch den Konstruktor erledigt. Zudem entscheidet man sich mit dem Konstruktoraufruf über die Art des nachfolgenden Zugriffs. Das Anlegen etwa eines FileInputStream-Objektes bedeutet zum einen bereits das Öffnen der Datei und des weiteren, daß man die Datei nur lesen kann. Dafür stellt die Klasse read()-Methoden zur Verfügung. Analog bedeutet der Konstruktoraufruf für FileOutputStream-Objekt das Öffnen einer Datei ausschließlich zum nachfolgenden Schreiben in diese Datei. Dafür stellt diese Klasse write()-Methoden zur Verfügung. Mit der Methode close() schließt man eine nicht mehr benötigte Datei. Obige drei Schritte nach Java übersetzt sehen wie folgt aus:

Eine wichtige "Kleinigkeit" fehlt allerdings noch. Anders als etwa eine Zuweisung String hallo="hola" ist der Zugriff auf eine Datei immer ein Experiment. Es kann gelingen oder auch nicht. Es gibt eine Reihe von Fehlern, die auftreten können, der Dateiname kann falsch sein, weil ihn ein Benutzer falsch eingegeben hat oder weil die Datei inzwischen nicht mehr existiert. Vielleicht hat man keine Zugriffsrechte, weil die Datei bereits exklusiv im Zugriff ist, vielleicht kann man sie nur zum Lesen öffnen, aber nicht zum schreiben usw. Selbst das Schließen einer Datei kann schiefgehen. Deswegen zwingt uns Java zu einer Fehlerbehandlung und der Compiler "klopft uns auf die Finger". Bei jedem der drei Vorgänge kann eine Exception geworfen werden, die entweder mit try catch abgefangen werden muß oder die man mit throws weiterwerfen muß.


FileNotFoundException ist eine Unterklasse von IOException. Fängt man also letzere ab, dann hat man auch die erste abgefangen (analog für das Werfen). Hier ein Beispiel, das eine Javadatei liest und auf die Konsole ausgibt.

FileReader fr=null;
String fileName="wzlbrmpft.java";
try
{
   fr = new FileReader(fileName);

   int ch;
   while( (ch=fr.read()) != -1 )
      System.out.print((char)ch);

   System.out.println();
}
catch(IOException ex)
{
   System.out.println(ex + "happened");
}
finally
{
   try
   {
      fr.close();
   }
   catch(IOException ex)
   {
   }
}

Warum liefern die read()-Methoden int und nicht byte oder char

Seit den Frühzeiten der Programmierung gibt es Dateilesemethoden (bzw. damals Funktionen oder Routinen genannt), die -1 zurückgeben, wenn das Ende einer Datei ereicht ist. Oft gibt es sogar eine Konstante EOF, die den Wert -1 besitzt. Alle diese Methoden geben jedoch ein int zurück, obwohl sie nur ein byte oder ein char lesen - und das muß auch so sein! Die binäre Darstellung von -1 ist nämlich abhängig vom Datentyp. Hier mal einige Darstellungen der Zahl -1 mit verschiedenen Datentypen.

Datentyp Bitfolge für -1 Bedeutung
byte 11111111
255   als vorzeichenlose Zahl interpretiert
-1   als vorzeichenbehaftete Zahl interpretiert
  (in Java immer vorzeichenbehaftet)
  als Zeichen im erweiterten Standard-ASCII-code
short 11111111  11111111
65535   als vorzeichenlose Zahl interpretiert
-1
 
  als vorzeichenbehaftete Zahl interpretiert
  (in Java immer vorzeichenbehaftet)
  als Zeichen im erweiterten Standard-ASCII-code
char 11111111  11111111
65535  als vorzeichenlose Zahl interpretiert
\uffff
 
  letztes im Unicode darstellbares Zeichen
  (wird zur Zeit nicht verwendet).
int 11111111  11111111  11111111  11111111
4 294 967 295   als vorzeichenlose Zahl interpretiert
-1
 
  als vorzeichenbehaftete Zahl interpretiert
  (in Java immer vorzeichenbehaftet)
EOF   Dateiendekennungszeichen

Da die Bitfolge 11111111 ein Zeichen des ASCII-codes ist, kann man sie nicht als Kennung für das Dateiende verwenden.










Valid XHTML 1.0 Strict top Back Next Up Home