JAVA NIO Scatter/Gather(矢量IO)

来源:互联网 发布:淘宝消保30元的条件 编辑:程序博客网 时间:2024/06/05 15:25
矢量IO=Scatter/Gather:
 
在多个缓冲区上实现一个简单的IO操作。减少或避免了缓冲区拷贝和系统调用(IO)
 
write:Gather
数据从几个缓冲区顺序抽取并沿着通道发送,就好比全部缓冲区全部连接起来放入一个大的缓冲区进行发送,缓冲区本身不具备gather能力。
read:Scatter

从通道读取的数据会按顺序散布到多个缓冲区,直到缓冲区被填满或者通道数据读完。


 

 

Gather:
Scatter:
示例代码
 / **  *散点  * <br> ------------------------------ <br>  * @param fileName  * @throws IOException  * @see FileChannel.read(java.nio.ByteBuffer [])  * /  private static void  scatter(final  String fileName)  throws  IOException {        RandomAccessFile accessFile =  new  RandomAccessFile(fileName,  “r” );      //获取文件通道      FileChannel channel = accessFile.getChannel();      //创建两个缓冲区      ByteBuffer headBuffer = ByteBuffer.allocate(2 );      ByteBuffer bodyBuffer = ByteBuffer.allocate(1024 );            ByteBuffer [] allBuffers =  new  ByteBuffer [] {headBuffer,bodyBuffer};      // headBuffer前10个字节      // bodyBuffer剩下的       long  n = channel.read(allBuffers);      System.out.println(“共读到多少字节:”  + n);            headBuffer.flip();      // head缓冲区中的数据:qw      System.out.println(“头缓冲区中的数据:”  + charset.decode(headBuffer));            bodyBuffer.flip();      // body缓冲区中的数据:ertyuiop      System.out.println(“body缓冲区中的数据:”  + charset.decode(bodyBuffer));      accessFile.close();      channel.close();  }    / **  *散点2  * <br> ------------------------------ <br>  * @param fileName  * @throws IOException  * @see FileChannel.read(java.nio.ByteBuffer [],int,int)  * /  private static void  scatter2(final  String fileName)  throws  IOException {        RandomAccessFile accessFile =  new  RandomAccessFile(fileName,  “r” );      //获取文件通道      FileChannel channel = accessFile.getChannel();      //创建五个缓冲区      ByteBuffer headBuffer = ByteBuffer.allocate(2 );      ByteBuffer bodyBuffer1 = ByteBuffer.allocate(3 );      ByteBuffer bodyBuffer2 = ByteBuffer.allocate(2 );      ByteBuffer bodyBuffer3 = ByteBuffer.allocate(2 );      ByteBuffer bodyBuffer4 = ByteBuffer.allocate(1 );            ByteBuffer [] allBuffers =  new  ByteBuffer [] {              headBuffer,               bodyBuffer1,bodyBuffer2,              bodyBuffer3,bodyBuffer4,};      // 0从那个缓冲区开始被使用使用3个缓冲区      //会使用headBuffer,bodyBuffer1,bodyBuffer2      长 N = channel.read(allBuffers,  0 ,  3 );            System.out.println(“共读到多少字节:”  + n);            headBuffer.flip();      // head缓冲区中的数据:qw      System.out.println(“头缓冲区中的数据:”  + charset.decode(headBuffer));            bodyBuffer1.flip();      // body1缓冲区中的数据:ert      System.out.println(“ body1缓冲区中的数据:”  + charset.decode(bodyBuffer1));            bodyBuffer2.flip();      // body2缓冲区中的数据:yu      System.out.println(“body2缓冲区中的数据:”  + charset.decode(bodyBuffer2));            bodyBuffer3.flip();      // body3,没有数据      System.out.println(“body3缓冲区中的数据:”  + charset.decode(bodyBuffer3));            bodyBuffer4.flip();      // body4没有数据      System.out.println(“body4缓冲区中的数据:”  + charset.decode(bodyBuffer4));            accessFile.close();      channel.close();  }    / **  *  * <br> ------------------------------ <br>  * @param fileName  * @throws IOException  * /  private static void  writeData(final  String fileName,String data)  throws  IOException {        RandomAccessFile accessFile =  new  RandomAccessFile(fileName,  “rw” );      accessFile.writeBytes(data);      accessFile.close();  }  

private static  Charset charset = Charset.forName(“GBK” );     public static void  main(String [] args)  throws  IOException {        final  String fileName =  “D:/test.log” ;      //先写入10个字节数据以便测试分散模式      writeData(fileName,  “qwertyuiop” );            /** - - - - - 分散 - - - - - - */      // read(java.nio.ByteBuffer [])      scatter(fileName);            // read(java.nio.ByteBuffer [],int,int)      scatter2(fileName);  }  

/ **  *聚集  * <br> ------------------------------ <br>  * @param fileName  * @throws IOException   * @see FileChannel#write(java.nio.ByteBuffer [])  * /  private static void  gather(String fileName)  throws  IOException {        RandomAccessFile accessFile =  new  RandomAccessFile(fileName,  “rw” );      //获取文件通道      FileChannel channel = accessFile.getChannel();      //创建两个缓冲区      ByteBuffer headBuffer = ByteBuffer.allocate(3 );      headBuffer.put(“abc” .getBytes());            ByteBuffer bodyBuffer = ByteBuffer.allocate(1024 );      bodyBuffer.put(“defg” .getBytes());            ByteBuffer [] allBuffers =  new  ByteBuffer [] {headBuffer,bodyBuffer};            headBuffer.flip();      bodyBuffer.flip();            //将按ALLBuffers顺序写入abcdefg      long  n = channel.write(allBuffers);            System.out.println(“共写入多少字节:”  + n);            accessFile.close();      channel.close();  }    / **  * gather2  * <br> ------------------------------ <br>  * @param fileName  * @throws IOException   * @see FileChannel#write(java.nio.ByteBuffer [],int,int)  * /  private static void  collect2(String fileName)  throws  IOException {        RandomAccessFile accessFile =  new  RandomAccessFile(fileName,  “rw” );      //获取文件通道      FileChannel channel = accessFile.getChannel();      //创建两个缓冲区      ByteBuffer headBuffer = ByteBuffer.allocate(3 );      ByteBuffer bodyBuffer1 = ByteBuffer.allocate(4 );      ByteBuffer bodyBuffer2 = ByteBuffer.allocate(20 );      ByteBuffer bodyBuffer3 = ByteBuffer.allocate(20 );      ByteBuffer bodyBuffer4 = ByteBuffer.allocate(20 );            headBuffer.put(“abc” .getBytes());      bodyBuffer1.put(“defg” .getBytes());      bodyBuffer2.put(“bnbnbnb” .getBytes());      bodyBuffer3.put(“zzz444” .getBytes());            ByteBuffer [] allBuffers =  new  ByteBuffer [] {              headBuffer,               bodyBuffer1,bodyBuffer2,              bodyBuffer3,bodyBuffer4,};            headBuffer.flip();      bodyBuffer1.flip();      bodyBuffer2.flip();      bodyBuffer3.flip();      bodyBuffer4.flip();            //将按allBuffers数组顺序使用两个缓冲区      // 0从哪开始      // 2使用几个      //当前使用headBuffer bodyBuffer1      //最终写入abcdefg      长 N = channel.write(allBuffers,  0 ,  2 );            //应该返回7个字节      System.out.println(“共写入多少字节:”  + n);            accessFile.close();      channel.close();  }  

private static  Charset charset = Charset.forName(“GBK” );     public static void  main(String [] args)  throws  IOException {        final  String fileName =  “D:/test.log” ;      /** - - - - - 收集 - - - - - - */      // FileChannel#write(java.nio.ByteBuffer [])      gather(fileName);            // FileChannel#write(java.nio.ByteBuffer [],int,int)      gather2(fileName);  }  



0 0
原创粉丝点击