zoukankan      html  css  js  c++  java
  • 十七、Java NIO AsynchronousFileChannel

    所有文章

    https://www.cnblogs.com/lay2017/p/12901123.html

    正文

    在Java7的时候,加入了AsynchronousFileChannel,使得你可以进行异步地read或write操作。本文关于如何使用AsynchronousFileChannel。

    创建一个AsynchronousFileChannel

    Path path = Paths.get("data/test.xml");
    
    AsynchronousFileChannel fileChannel = AsynchronousFileChannel.open(path, StandardOpenOption.READ);

    读取数据

    读取数据有两种方式

    通过Future读取

    通过read获取Future,read方法会立即返回

    Future<Integer> operation = fileChannel.read(buffer, 0);

    下面是一个完整示例

    AsynchronousFileChannel fileChannel = AsynchronousFileChannel.open(path, StandardOpenOption.READ);
    
    ByteBuffer buffer = ByteBuffer.allocate(1024);
    long position = 0;
    
    Future<Integer> operation = fileChannel.read(buffer, position);
    
    while(!operation.isDone());
    
    buffer.flip();
    byte[] data = new byte[buffer.limit()];
    buffer.get(data);
    System.out.println(new String(data));
    buffer.clear();

    示例中read直接返回了Future,通过Future不断轮询是否完成。完成以后,数据已经进入buffer。再从buffer读取数据并打印

    通过CompletionHandler

    除了通过Future主动轮询之外,还可以通过CompletionHandler接口的回调处理,示例代码如下

    fileChannel.read(buffer, position, buffer, new CompletionHandler<Integer, ByteBuffer>() {
        @Override
        public void completed(Integer result, ByteBuffer attachment) {
            System.out.println("result = " + result);
    
            attachment.flip();
            byte[] data = new byte[attachment.limit()];
            attachment.get(data);
            System.out.println(new String(data));
            attachment.clear();
        }
    
        @Override
        public void failed(Throwable exc, ByteBuffer attachment) {
    
        }
    });

    我们看到,completed在正常回调的时候触发。failed回调在失败的时候触发

    写入数据

    与读取数据类似,写入数据同样支持两种方式

    通过Future写入

    Path path = Paths.get("data/test-write.txt");
    AsynchronousFileChannel fileChannel = AsynchronousFileChannel.open(path, StandardOpenOption.WRITE);
    
    ByteBuffer buffer = ByteBuffer.allocate(1024);
    long position = 0;
    
    buffer.put("test data".getBytes());
    buffer.flip();
    
    Future<Integer> operation = fileChannel.write(buffer, position);
    buffer.clear();
    
    while(!operation.isDone());
    
    System.out.println("Write done");

    写入数据要注意file必须存在,否则会抛出NoSuchFileException。你可以这样创建文件

    if(!Files.exists(path)){
        Files.createFile(path);
    }

    通过CompletionHandler

    Path path = Paths.get("data/test-write.txt");
    if(!Files.exists(path)){
        Files.createFile(path);
    }
    AsynchronousFileChannel fileChannel = AsynchronousFileChannel.open(path, StandardOpenOption.WRITE);
    
    ByteBuffer buffer = ByteBuffer.allocate(1024);
    long position = 0;
    
    buffer.put("test data".getBytes());
    buffer.flip();
    
    fileChannel.write(buffer, position, buffer, new CompletionHandler<Integer, ByteBuffer>() {
    
        @Override
        public void completed(Integer result, ByteBuffer attachment) {
            System.out.println("bytes written: " + result);
        }
    
        @Override
        public void failed(Throwable exc, ByteBuffer attachment) {
            System.out.println("Write failed");
            exc.printStackTrace();
        }
    });

    和read类似,write正常结束会回调completed,失败回调failed。

  • 相关阅读:
    调试SQLSERVER (二)使用Windbg调试SQLSERVER的环境设置
    调试SQLSERVER (一)生成dump文件的方法
    SQLSERVER中如何快速比较两张表的不一样
    Leptonica在VS2010中的编译及简单使用举例
    UVALive 3135--Argus+自己定义优先队列的优先规则
    mysql---总体备份和增量备份
    OllyDbg 使用笔记 (十二)
    《TCP/IP具体解释卷2:实现》笔记--IP:网际协议
    blurImage做图片模糊处理报错free(): invalid next size
    docker网络配置方法总结
  • 原文地址:https://www.cnblogs.com/lay2017/p/12916545.html
Copyright © 2011-2022 走看看