Channel and Buffer
一:總體
Channel 和 buffer 是 NIO 是兩個最基本的數據類型抽象。
數據源--》通道(read)--》Buffer-->通道(write)-->數據匯
Buffer:
是一塊連續的內存塊。
是 NIO 數據讀或寫的中轉地。
Channel:
數據的源頭或者數據的目的地
用於向 buffer 提供數據或者讀取 buffer 數據 ,buffer 對象的唯一接口。
異步 I/O 支持
數據從channel(源頭)讀入buffer中:channel-->buffer
數據從buffer寫入channel(目的地)中:buffer->channel
主要的channel:
FileChannel,DatagramChannel,SocketChannel,ServerSocketChannel
主要Buffer:
ByteBuffer,CharBuffer,DoubleBuffer,FloatBuffer
二:Buffer的數據讀寫步驟
1寫入數據到buffer
2調用flip方法
3從Buffer中讀取數據
4調用clear()方法
向Buffer中寫入數據:
1)從channel寫入Buffer:inChannel.read(buffer)
2)通過buffer的put方法自己放入數據
從Buffer中讀取數據:
1)從Buffer讀取數據到Channel:outChannel.write(buffer)
2)使用buffer的get()方法
三:Channel
1 FileChannel:一個連接到文件的通道,可以通過它來讀寫文件
2 SocketChannel:一個連接到TCP網絡套接字的通道
1)打開一個SocketChannel並連接到互聯網上的某臺服務器
SocketChannel sc = SocketChannel.open();
sc.connect(new InetSocketAddress(""));
2)當一個新的連接到達ServerSocketChannel時,會創建一個SocketChannel
3 ServerSocketChannel:一個可以監聽新進來的TCP連接的通道
ServerSocketChannel c = ServerSocketChannel.open();
c.socket.bind(new InetSocketAddress(""));
while(true){
SocketChannel sc = c.accept();
}
Selector:
能夠檢測一到多個NIO通道,並能夠知曉通道是否爲諸如讀寫時間做好準備的組件,這樣一個單獨的線程可以管理多個Channel,從而管理多個網路連接
允許單線程中處理多個channel(例如聊天服務器,應用打開了多個連接,但每一個的流量都很低)
Thread->Selector->Channel1
->Channel2
->Channel3
1創建:Selector.open();
2 向selector註冊通道
channel.configurBlocking(false);
channel.register(selector,SelectionKey.OP_READ);
3 使用selector選擇通道
Set selectedKeys = selector.selectedKeys();
Iterator keys = selectedKeys.iterator();
while(keys.hasNext()){
SelectionKey key = keys.next();
...
}
Scatter/Gather
scatter:分散,從channel中讀取數據,並寫入多個buffer中
Gather:聚集,將數據從多個buffer中寫入到同一個channel