Java NIO (一)--简介

一、简介


Java NIO (New IO)是JDK1.4后引入的新输入/输出API,提供基于缓冲区(buffer)的块写入/读取,而以前的I/O是基于流(Stream)的方式,NIO基于块的IO操作,将最耗时的缓存区读取和填充交由底层操作系统实现,因此速度上要快得多;主要由以下三个核心部分组成: 
1.Channel
2. Buffer 
3. Selector

二、Channel - 通道

通道可以理解为以前的“流”,数据从通道读取,也可以向通道写入数据,是双向的,但是读取和写入都必须是使用Buffer,即读取数据时,需要从通道读取到缓存区,然后再从缓冲区获取数据,写入数据也需要先将数据写入到缓存区,再将缓冲区写入通道;

NIO中主要有以下通道类型: 
- FileChannel - 文件IO 
- DatagramChannel - UDP传输 
- SocketChannel - TCP传输 
- ServerSocketChannel -TCP传输

三、Buffer - 缓冲区

缓冲区可以认为是一个数据容器,可以理解为一个基本数据类型数组,如字节数组等;NIO中任何数据输入/输出都是必须经由缓冲区实现,主要有以下缓冲区类型: 
- ByteBuffer 
- CharBuffer 
- ShortBuffer 
- IntBuffer 
- LongBuffer 
- FloatBuffer 
- DoubleBuffer 
- MappedByteBuffer

可以看出以上类型覆盖Java的全部基本类型,MappedByteBuffer(内存映射文件,后续章节讲解)对于每种Buffer都有相同的方法,只有ByteBuffer拥有部分特殊的方法

向Buffer中写数据 

写数据到Buffer有两种方式: 

·        从Channel写到Buffer。

·        通过Buffer的put()方法写到Buffer里。

从Channel写到Buffer的例子 : 

int bytesRead = inChannel.read(buf); //read into buffer.
通过put方法写Buffer的例子:

buf.put(127);  

从Buffer中读取数据 

从Buffer中读取数据有两种方式: 

·        从Buffer读取数据到Channel。

·       使用get()方法从Buffer中读取数据。


从Buffer读取数据到Channel的例子:

 //read from buffer into channel.  
 int bytesWritten = inChannel.write(buf);
使用get()方法从Buffer中读取数据的例子 :
byte aByte = buf.get(); 


四、Selector - 选择器

选择器支持单个线程处理多个Channel,将多个Channel注册到一个选择器中,选择器基于事件的方式处理;从选择器获取注册Channel中关注的事件(如读、写)并进行数据处理,非常适用于多个数据量不大、读写不频繁的通道,使用单个线程来处理;


五、NIO简单(标准)的输入/输出

一个简单(标准)的NIO输入输出一般包含如下步骤: 
1. 从数据源获取通道 
2. 分配缓冲区 
3. 切换缓存区为写模式 
4. 从通道读取数据写入缓冲区 
5. 切换缓冲区为读模式 
6. 缓冲区数据写入通道中 
7. 关闭资源

实例代码如下:

package com.denny.aio.test;

import java.io.IOException;
import java.io.RandomAccessFile;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;

public class Test {

	public static void main(String[] args) throws IOException {
		
		RandomAccessFile formFile = new RandomAccessFile("src\\a.txt", "rw");
		RandomAccessFile toFile = new RandomAccessFile("src\\b.txt", "rw");
		
		//获取channel
		FileChannel fromChannel = formFile.getChannel();
		FileChannel toChannel = toFile.getChannel();
		
		// 定义缓冲大小
		int bufSize = 1024*4;
		
		// 定义缓冲
		ByteBuffer byteBuffer = ByteBuffer.allocate(bufSize);
		
		int len = 0;
		
		// 将数据从源channel写入到缓冲区
		while(  (len=fromChannel.read(byteBuffer)) !=-1 ){
			
			//切换到读模式
			byteBuffer.flip();
			
			//读取缓冲区数据写到目标channel
			toChannel.write(byteBuffer);
			
			// 清空缓冲
			byteBuffer.clear();
		}
		
		// 释放资源
		toChannel.close();
		fromChannel.close();
	}
}


你可能感兴趣的:(JavaSE,NIO)