InputStream
InputStream 就是Java標準庫提供的最基本的輸入流。它位於 java.io 這個包裏。 java.io 包提供了所有同步IO的功能。要特別注意的一點是, InputStream 並不是一個接口,而是一個抽象類,它是所有輸入流的超類。這個抽象類定義的一個最重要的方法就是 int read()
.這個方法會讀取輸入流的下一個字節,並返回字節表示的 int 值(0~255)。如果已讀到末尾,返回 -1 表示不能繼續讀取了。
我們還要注意到在讀取或寫入IO流的過程中,可能會發生錯誤,例如,文件不存在導致無法讀取,沒有寫權限導致寫入失敗,等等,這些底層錯誤由Java虛擬機自動封裝成 IOException 異常並拋出。因此,所有與IO操作相關的代碼都必須正確處理IOException
。
其實現類有FileInputStream、ByteArrayInputStream
緩衝
在讀取流的時候,一次讀取一個字節並不是最高效的方法。很多流支持一次性讀取多個字節到緩衝區,對於文件和網絡流來說,利用緩衝區一次性讀取多個字節效率往往要高很多。 InputStream 提供了兩個重載方法來支持讀取多個字節:
int read(byte[] b)
:讀取若干字節並填充到 byte[] 數組,返回讀取的字節數
int read(byte[] b, int off, int len)
:指定 byte[] 數組的偏移量和最大填充數
Reader
Reader是Java的IO庫提供的另一個輸入流接口。和 InputStream 的區別是, InputStream 是一個字節流,即以 byte 爲單位讀取,而Reader 是一個字符流,即以 char 爲單位讀取。
InputStreamReader
Reader 和 InputStream 有什麼關係?
除了特殊的 CharArrayReader 和 StringReader ,普通的 Reader 實際上是基於 InputStream 構造的,因爲 Reader 需要從 InputStream 中讀入字節流( byte ),然後,根據編碼設置,再轉換爲 char 就可以實現字符流。如果我們查看 FileReader 的源碼,它在內部實際上持有一個 FileInputStream 。既然 Reader 本質上是一個基於 InputStream 的 byte 到 char 的轉換器,那麼,如果我們已經有一個 InputStream ,想把它轉換爲 Reader ,是完全可行的。 InputStreamReader 就是這樣一個轉換器,它可以把任何 InputStream 轉換爲 Reader 。
Scanner
Scanner類可以很方便地輸入,它也可以設置讀取的分隔符,如用.
分割
scan.useDelimiter(".");