ByteBuffer前先後後看過好幾回了,實際使用也用了一些,總以爲條理不夠清晰。java
《程序員的思惟修煉》一本書講過,主動學習,要比單純看資料效果來的好,因此乾脆寫個詳細點的文章來記錄一下。程序員
ByteBuffer是NIO裏用得最多的Buffer,它包含兩個實現方式:HeapByteBuffer
是基於Java堆的實現,而DirectByteBuffer
則使用了unsafe
的API進行了堆外的實現。這裏只說HeapByteBuffer。數組
ByteBuffer最核心的方法是put(byte)
和get()
。分別是往ByteBuffer裏寫一個字節,和讀一個字節。緩存
值得注意的是,ByteBuffer的讀寫模式是分開的,正常的應用場景是:往ByteBuffer裏寫一些數據,而後flip(),而後再讀出來。post
這裏插兩個Channel方面的對象,以便更好的理解Buffer。學習
ReadableByteChannel
是一個從Channel中讀取數據,並保存到ByteBuffer的接口,它包含一個方法:code
<!-- lang: java --> public int read(ByteBuffer dst) throws IOException;
WritableByteChannel
則是從ByteBuffer中讀取數據,並輸出到Channel的接口:對象
<!-- lang: java --> public int write(ByteBuffer src) throws IOException;
那麼,一個ByteBuffer的使用過程是這樣的:接口
<!-- lang: java --> byteBuffer = ByteBuffer.allocate(N); //讀取數據,寫入byteBuffer readableByteChannel.read(byteBuffer); //變讀爲寫 byteBuffer.flip(); //讀取byteBuffer,寫入數據 writableByteChannel.write(byteBuffer);
看到這裏,通常都不太明白flip()幹了什麼事,先從ByteBuffer結構提及:ip
buff即內部用於緩存的數組。
當前讀取的位置。
爲某一讀過的位置作標記,便於某些時候回退到該位置。
初始化時候的容量。
讀寫的上限,limit<=capacity。
寫模式下,往buffer裏寫一個字節,並把postion移動一位。寫模式下,通常limit與capacity相等。
寫完數據,須要開始讀的時候,將postion復位到0,並將limit設爲當前postion。
從buffer裏讀一個字節,並把postion移動一位。上限是limit,即寫入數據的最後位置。
將position置爲0,並不清除buffer內容。
mark相關的方法主要是mark()
(標記)和reset()
(回到標記),比較簡單,就不畫圖了。