JAVA流和文件

 

流和文件

     輸入和輸出技術並不那麼令人興奮,如果沒有讀寫數據的能力,編寫出來的程序會受到很大的限制。

 

一、

輸入流:一個可以讀取字節序列的對象被稱爲輸入流(input stream)。

輸出流:一個可以寫入字節序列的對象被稱爲輸出流(output stream)。

在抽象類InputStreamOutputStream中對他們進行了說明,初次之外,由

於以字節爲單位的流處理存儲爲Unicode碼的信息很不方便,所以有一個專門的類層次來處理Unicode字符,這些類繼承於抽象類ReaderWriter。它們的讀寫操作都是基於雙字節的Unicode代碼單元,而不是基於單字節。

4種抽象類派生的具體類組成了一個Java“動物園”。在這個動物園中幾乎可以看到各種像得到的輸入/輸出“動物”。

        API  java.io.InputStream 1.0

Abstract int read()

Int read (byte[] b)

Int read (byte[]b ,int off, int len)

Long skip(long n)

Int available()

Void close ()

Void mark(int readlimit)

Void reset()

Boolean markSupported()

        API  java.io.OutputStream 1.0

Abstract void write(int n)

Void write(byte[] b)

Void close()

Void flush()

ReaderWriter類的基本方法和InputStream以及OutputStream類非常類似。

       Abstract int read()

       Abstract void write(int b)

 

 

二、常用的流

1、字節流

inputStream---------à FilterInputStream------àDataInputStream

outputStream-----àFilterOutputStream----àDataOutputStream

DataInputStreamDataOutputStream能夠讀寫所有的基本的Java類型。

 

DataInputStream實現了 DataInput 接口:

             API   java.io.DataInput 1.0

Boolean readBoolean()

Byte readByte()

Double readDouble()

Float readFloat()

Int readInt()

String readUTF()

     DataOutputStream 實現了DataOutput 接口:

             API   java.io.DataOutput 1.0

Void writeBoolean(Boolean b)

Void writeByte(byte b)

Void writeDouble(double d)

Void writeInt(int  i);

Void writeUTF(String s);

   

inputStream---------à FileInputStream

outputStream-----àFileOutputStream

FileInputStreamFileOutputStream能夠把輸入和輸出流與磁盤文件關聯起來。

例:FileInputStream fin = new FileInputStream(“employee.dat”);

將在當前路徑下尋找名爲“employee.dat”的文件。

    例:FileInputStream fin = new FileInputStream(“C://yuyifan//employee.dat”);

例:FileInputStream fin = new FileInputStream(“C:/yuyifan/employee.dat”);

例:File f = new File(“employee.dat”);

    FileInputStream fin = new FileInputStream(f);

 

FileInputStream沒有讀取數值類型的方法一樣,DataInputStream也沒有從文件中讀取數值的方法。

Java使用了一種很聰明的策略來劃分這兩種職責。一些流可以從文件及其其他地方接受字節,另一些流可以將字節組合成更加有用的數據類型。

Java程序員採用將一種已經存在的流傳遞給另一個流的構造器方法,將這兩種流結合起來,結合後的流被稱爲過濾流。

例:FileInputStream fin = new FileInputStream(“employee.dat”);

    DataInputStream din = new DataInputStream(fin);

    Double s =din.readDouble();

 

 

inputStream---------à FilterInputStream------àBufferedInputStream

outputStream-----àFilterOutputStream----àBufferedOutputStream

 

在默認情況下,流是不能進行緩衝處理的。換句話說,每次對流進行read讀取都要求操作系統發送一個字節。所以——————————:

例:DataInputStream din = new DataInputStream(new BufferedInputStream(new FileInputStream(“employee.dat”)));

inputStream---------à FilterInputStream------àInflaterInputStream---àZipInputStream

 

outputStream-----àFilterOutputStream----àInflaterOutputStream--àZipOutputSteam

 

例:ZipnputStream zin = new ZipInputStream(new FileInputStream(“employee.zip”));

     DataInputStream din = new DataInputStream(zin);

 

RandomAccessFile流類能夠在文件的任何位置查找或者寫入數據,它同時實現了DataInputDataOutput接口。打開一個隨機存取文件,要麼進行只讀操作,要麼進行讀寫操作。

例:RandomAccessFile in = new RandomAccessFile(“employee.dat”,”r”);

    RandomAccessFile inout = new RandomAccessFile(“employee.dat”,”rw”);

隨機存取文件同時提供了一個文件指針。文件指針總是指向下一條要進行讀寫操作記錄的位置。Seek方法將文件指針設定在文件內部的任意字節位置。getFilePointer方法返回的是文件指針的當前位置。

        API  java.io.RandomAccessFile 1.0

RandomAccessFile(String file ,String mode)

RandomAccessFile(File file, String mode);

Long getFilePointer()

Void seek(long pos)

Long length()

2、文本流

   Read ----àInputStreamReader-àFileReader

   Writer--àOutputSteamWriter--àFileWriter

   重點:文本文件的I/O

   例:InputStreamReader    in = new InputStreamReader(System.in);

       InputStreamReader in = new InputStreamReader(new FileInputStream(“yyf.dat”),”ISO8859_5”);

     

      FileWriter out = new FileWriter(“output.txt”);

      相當於

      FileWriter out = new FileWriter(new FileOutputStream(“output.txt”));

 

 

  進行文本輸出時,應該使用PrintWriter. PrintWriter可以以文本格式打印字符串和數值。 一個PrintWriter必須與一個目標writer相結合。

  例:PrintWriter out = new PrintWriter(new FileWriter(“employee.txt”));

  例:PrintWriter out = new PrintWriter(new FileOutputStream(“employee.txt”));

 

  代碼片斷:

      String name = YYf”;

      Double salary = 6700;

      Out.print(name);

      Out.print(‘ ’);

      Out.println(“salary”);

 

  例:PrintWriter out = new PrintWriter(new FileWriter(“employee.txt”),true);

   

   如果writer被設爲自動刷新模式,任何時候調用println,緩衝區內的所有字符都會被送到其目的地。(printwriter 總是緩衝的。) 默認情況下,自動刷新不開啓。

 

 

JDK5.0以前,唯一用來處理文本輸入的是BufferedReader,在這個類中有一個readLine()方法,它能以行的方式讀取文本,並需要將一個緩衝的讀取器同一個輸入源接合起來。

例:  BufferedReader in = new BufferedRead(new FileReader(“employee.txt”));

      String line ;

      While( (line = in.readLine()) ! =null)

{

 //Do something with line

}

 

 

Zip文件流

   Zip文件(通常)以壓縮格式存儲一個或更多文件。Java1.1可以處理GZIPZIP格式。

  注意: 處理ZIP文件的類在java.util.zip中而不在java.io中,所以請記住要添加必要的import語句。儘管不是java.io的一部分,但GZIPZIP類還是java.io.FilterInputStreamjava.io.FilterOutputStream的子類。

  每個ZIP文件都有文件頭,其中包括了諸如文件名和使用的壓縮方法等信息。

代碼片斷:

  ZipInputStream zin = new ZipInputStream(new FileInputStream(zipname));

  ZipEntry entry;

  While((entry = zin.getNextEntry())!=null)

{

  // 分析 entry

   // zin 的內容

   //Zin.closeEntry();

}

Zin.close();

 

看例子 :打開一個ZIP文件。然後再屏幕的頂部的一個複合框中顯示出ZIP壓縮文件中存在的所有文件。如果雙擊其中一個文件,該文件的內容就會在文本區顯示出來。例子 ZipTest.java.

 

 

        API  java.util.zip.ZipInputStream1.1

ZipInputStream(InputStream in)

這個構造器創建一個ZipInputStream,它允許從給定的InputStream內讀取數據。

ZipEntry  getNextEntry()

返回下一條目的ZipEntry對象;如果沒有更多的條目的話,返回null

Void closeEntry()

關閉ZIP文件中當前打開的條目。隨後可以使用getNextEntry()讀取下一條目。

        API   java.util.zip.ZipOutputStream 1.1

ZipOutputStream(OutputStream out)

這個構造器創建了一個ZipOutputStream,使用它可以向指定的OutputStream內寫入壓縮數據。

Void   putNextEntry(ZipEntry ze)

將給定的ZipEntry的信息寫入流中,並且爲數據定位流。隨後可以使用write()把數據寫入流中。

 Void closeEntry()

關閉ZIP文件中當前打開的條目。隨後可以使用putNextEntry()方法開始對下一條目進行操作。

        API  java.util.zip.ZipEntry 1.1

ZipEntry(String name)

構造一個壓縮條目。

String getName()

返回該條目的名稱。

Long getSize()

返回該條目未經壓縮時的大小;如果未經壓縮時的大小未知,返回-1

Boolean isDirectory()

返回一個布爾值表明該條目是否爲一個目錄。

 

流的使用樣例:

1、將相同類型的多個對象中的實例變量保存的值以文本格式保存。

文件: DataFileTest.java

        API   java.util.StringTokenizer 1.0

StringTokenizer(String str ,String delim)

使用給定的分隔符集合構造一個字符串的記號處理器。

StringTokenizer(String str )

構造一個字符串的記號處理器,使用默認的分隔符集“/t/n/r

String hasMoreToken()

如果存在更多的記號則返回true.

String nextToken()

返回下一個記號,如果沒有記號,則拋出一個NoSuchElementException異常。

String nextToken(String delim)

在切換到新的分隔符集後,返回下一個記號,以後使用新的分隔符集。

Int countTokens()

返回在字符串中的記號個數。

樣例輸出:

Harry Hacker | 35500|1989|10|1

Carl Cracker|75000|1987|12|15

Tony Tester|38000|1990|3|15

2、將相同類型的多個對象中的實例變量保存的值以二進制格式保存。

RandomAccessFile類。

樣例文件:RandomFileTest.java

3、將多個對象以對象的形式保存。

樣例文件:ObjectFileTest.java

注意:所有要寫入文件的對象都要實現Serializable接口。

        API    java.io.ObjectOutputStream

ObjectOutputStream(OutputStream out)

Void writeObject(Object obj)

        API   java.io.ObjectInputStream

ObjectInputStream(InputStream in)

Void readObject(Object obj)

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章