聲明:本系列只供本人自學(xué)使用,勿噴成黄。
IO是每位java工程師都必須掌握的知識(shí)點(diǎn)呐芥,無論什么項(xiàng)目都會(huì)涉及文件IO、網(wǎng)絡(luò)IO等慨默,但是java中的IO類多達(dá)幾十種贩耐,很多人在使用時(shí)會(huì)難以抉擇,并且網(wǎng)上關(guān)于IO的學(xué)習(xí)資料比較雜亂厦取,因此本人決定研究JDK8中rt.jar的java.io源碼并總結(jié)為系列文章,如有不正之處還請(qǐng)多多指點(diǎn)管搪。
網(wǎng)上的IO教程大多是一上來就扔個(gè)降視力的大圖虾攻,嚇得我等小白直接X掉網(wǎng)頁。本人痛定思痛更鲁,決定從0擴(kuò)展IO體系霎箍,首先我們按照操作單元進(jìn)行劃分,如下圖澡为。
程序中的所有數(shù)據(jù)都是以流的方式存儲(chǔ)或傳輸漂坏,通常情況下,二進(jìn)制數(shù)據(jù)(Binary)使用字節(jié)流傳輸、存儲(chǔ)顶别,文本數(shù)據(jù)(ASCII)使用字符流傳輸谷徙、存儲(chǔ)、讀取驯绎。
一完慧、字節(jié)流
1.InputStream
- 源碼結(jié)構(gòu)圖
- 核心方法
核心方法就是read,讀取InputStream并保存到byte[]
// 返回下一個(gè)字節(jié)剩失,如果沒有則返回-1
public abstract int read() throws IOException
// 實(shí)際調(diào)用read(b, 0, b.length);
public int read(byte b[]) throws IOException
public int read(byte b[], int off, int len) throws IOException{
1.參數(shù)檢查
2.循環(huán)read()屈尼,賦值給b
3.返回上一步賦值給b的字節(jié)數(shù)量
}
public void close() throws IOException
- 其余方法
// 跳過n個(gè)字節(jié)
public long skip(long n) throws IOException{
1. size=(常量MAX_SKIP_BUFFER_SIZE與入?yún)的較小值)
2. 循環(huán)read()賦值給臨時(shí)數(shù)組new byte[size]
}
// 返回InputStream的字節(jié)數(shù),但是并不準(zhǔn)確
public int available() throws IOException
// 標(biāo)記拴孤,回到標(biāo)記位脾歧,是否支持該功能
public synchronized void mark(int readlimit)
public synchronized void reset() throws IOException
public boolean markSupported()
2.OutputStream
- 源碼結(jié)構(gòu)圖
- 核心方法
核心方法就是write,將byte[]寫入OutputStream
public abstract void write(int b) throws IOException;
// 實(shí)際調(diào)用write(b, 0, b.length);
public void write(byte b[]) throws IOException
public void write(byte b[], int off, int len) throws IOException{
1.參數(shù)檢查
2.循環(huán)write()
}
// 保證字節(jié)數(shù)組傳遞給底層操作系統(tǒng)演熟,不能保證操作系統(tǒng)已完成寫入
public void flush() throws IOException
public void close() throws IOException
二鞭执、字符流
1.Reader
-
源碼結(jié)構(gòu)圖
- 構(gòu)造器
// 用來實(shí)現(xiàn)同步操作,子類如果需要同步绽媒,也應(yīng)使用synchronized (lock)
protected Object lock;
protected Reader() {
this.lock = this;
}
protected Reader(Object lock) {
if (lock == null) {
throw new NullPointerException();
}
this.lock = lock;
}
- 核心方法
核心方法就是read蚕冬,讀取Reader并保存到char[]
// 返回下一個(gè)字符,如果沒有則返回-1
public int read() throws IOException
// 實(shí)際調(diào)用read(cbuf, 0, cbuf.length);
public int read(char cbuf[]) throws IOException
abstract public int read(char cbuf[], int off, int len) throws IOException
//JDK5新增
public int read(java.nio.CharBuffer target) throws IOException{
1.讀取target.remaining()個(gè)字符到char[]
2.將char[]賦值給target
}
public void close() throws IOException
- 其余方法
// 跳過n個(gè)字節(jié)
public long skip(long n) throws IOException{
1. size=(常量maxSkipBufferSize與入?yún)的較小值)
2. 循環(huán)read()賦值給臨時(shí)數(shù)組new byte[size]
}
// 下一次read()是否阻塞
public boolean ready() throws IOException
// 標(biāo)記是辕,回到標(biāo)記位囤热,是否支持該功能
public synchronized void mark(int readlimit)
public synchronized void reset() throws IOException
public boolean markSupported()
2.Writer
-
源碼結(jié)構(gòu)圖
- 構(gòu)造器(同Reader)
// 用來實(shí)現(xiàn)同步操作,子類如果需要同步获三,也應(yīng)使用synchronized (lock)
protected Object lock;
protected Writer() {
this.lock = this;
}
protected Writer(Object lock) {
if (lock == null) {
throw new NullPointerException();
}
this.lock = lock;
}
- 核心方法
核心方法
① write旁蔼,將char[] 寫入Writer
② append,將CharSequence追加到Writer
// 以下方法實(shí)際調(diào)用write(char cbuf[], int off, int len)
public void write(int c) throws IOException
public void write(char cbuf[]) throws IOException
public void write(String str) throws IOException
public void write(String str, int off, int len) throws IOException
//JDK5新增
public Writer append(CharSequence csq) throws IOException
public Writer append(CharSequence csq, int start, int end) throws IOException
public Writer append(char c) throws IOException
abstract public void write(char cbuf[], int off, int len) throws IOException;
// 保證字符數(shù)組傳遞給底層操作系統(tǒng)疙教,不能保證操作系統(tǒng)已完成寫入
public void flush() throws IOException
public void close() throws IOException
三棺聊、總結(jié)
- 字節(jié)流通過字節(jié)數(shù)組byte[]進(jìn)行讀寫操作,InputStream核心方法是read(byte b[], int off, int len)贞谓,OutputStream核心方法是write(byte b[], int off, int len)
- 字符流通過字符數(shù)組char[]進(jìn)行讀寫操作限佩,Reader核心方法是read(char cbuf[], int off, int len),Writer核心方法是write(char cbuf[], int off, int len)
- 無論讀取哪種流裸弦,read返回值為-1表示結(jié)束祟同,其他值則表示已讀取到數(shù)組中的數(shù)量。
本節(jié)討論的類都是抽象類理疙,力求從宏觀上了解這些類各自的作用晕城,接下來的系列將深入具體的實(shí)現(xiàn)類源碼,并用簡(jiǎn)單demo示例進(jìn)行說明窖贤。由于輸入流砖顷、輸出流代碼相似贰锁,并且在使用時(shí)一般都成對(duì)出現(xiàn),下文也將成對(duì)講解滤蝠。