InputStream這個抽象類是所有基於字節的輸入流的超類,抽象了Java的字節輸入模型。在這個類中定義了一些基本的方法。看一下類的定義:
public abstract class InputStream implements Closeable
首先這是一個抽象類,實現了Closeable接口,也Closeable接口又拓展了AutoCloseable接口,因此所有InputStream及其子類都可以用於Java 7 新引入的帶資源的try語句。讀入字節之前,我們可能想要先知道還有多少數據可用,這有available方法完成,具體的讀入由read()及其重載方法完成,skip方法用於跳過某些字節,同時定義了幾個有關標記(mark)的方法,讀完數據使用close方法關閉流,釋放資源。下面詳細介紹各個方 法:
1. available方法
public int available() throws IOException
假設方法返回的int值為a,a代表的是在不阻塞的情況下,可以讀入或者跳過(skip)的字節數。也就是說,在該對象下一次調用讀入方法讀入a個字節,或者skip方法跳過a個字節時,不會出現阻塞(block)的情況。這個調用可以由相同線程調用,也可以是其他線程調用。但是在下次讀入或跳過的時候,實際讀入(跳過)的可能不只a字節。當遇到流結尾的時候,返回0。如果出現I/O錯誤,拋出IOException異常。看一下InputStream中該方法的實現:
public int available() throws IOException { return 0; }
2. 讀入方法:read
2.1 read()
public abstract int read()throws IOException
2.2 read(byte[] b)
public int read(byte b[]) throws IOException
2.3 read (byte[] b, int off, int len)
public int read(byte[] b,int off,int len) throws IOException
public int read(byte b[]) throws IOException { return read(b, 0, b.length); }

public int read(byte b[], int off, int len) throws IOException { if (b == null) { // 檢測參數是否為null throw new NullPointerException(); } else if (off < 0 || len < 0 || len > b.length - off) { throw new IndexOutOfBoundsException(); // 數組越界檢測 } else if (len == 0) { return 0; //如果b為空數組,返回0 } int c = read(); // 調用read()方法獲取下一個字節 if (c == -1) { return -1; } // 遇到流尾部,返回-1 b[off] = (byte)c; //讀入的第一個字節存入b[off] int i = 1; // 統計實際讀入的字節數 try { for (; i < len ; i++) { // 循環調用read,直到流尾部 c = read(); if (c == -1) { break; } b[off + i] = (byte)c; // 一次存入字節數組 } } catch (IOException ee) { } return i; // 返回實際讀入的字節數 }
3. skip方法
public long skip(long n)throws IOException
這個方法試圖跳過當前流的n個字節,返回實際跳過的字節數。如果n為負數,返回0.當然子類可能提供不能的處理方式。n只是我們的期望,至於具體跳過幾個,則不受我們控制,比如遇到流結尾。修改上面的例子:


public long skip(long n) throws IOException { long remaining = n; // 還有多少字節沒跳過 int nr; if (n <= 0) { return 0; // n小於0 簡單返回0 } int size = (int)Math.min(MAX_SKIP_BUFFER_SIZE, remaining); // 這里的常數在類中定義為2048 byte[] skipBuffer = new byte[size]; // 新建一個字節數組,如果n<2048,數組大小為n,否則為2048 while (remaining > 0) { nr = read(skipBuffer, 0, (int)Math.min(size, remaining)); // 讀入字節,存入數組 if (nr < 0) { // 遇到流尾部跳出循環 break; } remaining -= nr; } return n - remaining; }
4.與標記相關的方法
4.1 mark
public void mark(int readlimit)

4.2 reset
public void reset()throws IOException
InputStream is = null; try { is = new BufferedInputStream(new FileInputStream("test.txt")); is.mark(4); is.skip(2); is.reset();
System.out.println((char)is.read()); } finally { if (is != null) { is.close(); } }
4.3 markSupported
public boolean markSupported()
檢測當前流對象是否支持標記。是返回true。否則返回false。比如InputStream不支持標記,而BufferedInputStream支持。
5. close方法
public void close()throws IOException
關閉當前流,釋放與該流相關的資源,防止資源泄露。在帶資源的try語句中將被自動調用。關閉流之后還試圖讀取字節,會出現IOException異常。