//使用nio流读写文件
private static void useNioRWfile(String inFile, String outFile)
throws FileNotFoundException, IOException {
//获取源文件和目标文件的输入输出流
FileInputStream fin = new FileInputStream(inFile);
FileOutputStream fos = new FileOutputStream(outFile);
try{
//获取输入输出通道
FileChannel fcin = fin.getChannel();
FileChannel fcout = fos.getChannel();
//创建1024字节的缓存区
ByteBuffer buffer = ByteBuffer.allocate(1024);
long start = System.currentTimeMillis();
while(true){
//重设此缓冲区,使它可以接受读入的数据。Buffer对象中的limit=capacity;
buffer.clear();
//从输入通道中将数据读入到缓冲区
int temp = fcin.read(buffer);
if(temp == -1){
break;
}
//让缓冲区将新入读的输入写入另外一个通道.Buffer对象中的limit=position
buffer.flip();
//从输出通道中将数据写入缓冲区
fcout.write(buffer);
}
System.out.println("总共耗时:"+(System.currentTimeMillis()-start)+"ms");
} finally {
if(fin!=null) fin.close();
if(fos != null) fos.close();
}
}
例子中的buffer.clear()跟buffer.flip()的用法
clear() 方法重设缓冲区,使它可以接受读入的数据。 flip() 方法让缓冲区可以将新读入的数据写入另一个通道。
可以用三个值指定缓冲区在任意时刻的状态:
• position
• limit
• capacity
这三个变量一起可以跟踪缓冲区的状态和它所包含的数据。
Position
缓冲区实际上就是美化了的数组。在从通道读取时,您将所读取的数据放到底层的数组中。 position 变量跟踪已经写了多少数据。更准确地说,它指定了下一个字节将放到数组的哪一个元素中。因此,如果您从通道中读三个字节到缓冲区中,那么缓冲区的 position 将会设置为3,指向数组中第四个元素。
同样,在写入通道时,您是从缓冲区中获取数据。 position 值跟踪从缓冲区中获取了多少数据。更准确地说,它指定下一个字节来自数组的哪一个元素。因此如果从缓冲区写了5个字节到通道中,那么缓冲区的 position 将被设置为5,指向数组的第六个元素。
Limit
limit 变量表明还有多少数据需要取出(在从缓冲区写入通道时),或者还有多少空间可以放入数据(在从通道读入缓冲区时)。
position 总是小于或者等于 limit。
Capacity
缓冲区的 capacity 表明可以储存在缓冲区中的最大数据容量。实际上,它指定了底层数组的大小 ― 或者至少是指定了准许我们使用的底层数组的容量。
limit 决不能大于 capacity。
//使用普通的io流读写文件
private static void useIoRWfile(String inFile, String outFile)
throws FileNotFoundException, IOException {
//获取源文件和目标文件的输入输出流
FileInputStream fin = new FileInputStream(inFile);
BufferedInputStream bis=new BufferedInputStream(fin); //连接带缓冲的输入流
FileOutputStream fos = new FileOutputStream(outFile);
BufferedOutputStream bos=new BufferedOutputStream(fos); //连接带缓冲的输出流
try{
int temp = 0;
long start = System.currentTimeMillis();
while((temp=fin.read())!=-1){
bos.write(temp); //写数据
bos.flush(); //强制输出
}
System.out.println("总共耗时:"+(System.currentTimeMillis()-start)+"ms");
} finally {
if(fin!=null) fin.close();
if(fos != null) fos.close();
if(bis!=null) bis.close();
if(bos!=null) bos.close();
}
}
控制台打印输出为:===========总共耗时:406ms
没想到,这两种方式的效率方面会有这么大的差距,,,,,我想,应该就是NIO内部维护了一个更加效率高的Buffer缓冲数组对象。