Java中的异步执行Future小结

最近碰到的异步处理的操作比较多,异步就是不等想要的结果返回执行接下来的其他操作,等异步结果返回后直接调用已经注册好的处理方法完成后续操作。异步的思想是非常棒的,相比轮询的方式而言,异步的实现方式无疑是高效并且优雅的。本文介绍了包括Future,AIO和有点类似于单机版的Map-Reduce的fork/join框架。

Guava ListenableFuture

使用JDK提供的线程池ExcuteService的execute(Runable runable)方法来执行不需要返回结果的线程任务,而使用submit(Callable callable)方法需要线程任务返回T类型的执行结果,方法返回Future对象,使用Future的get方法可以获取执行结果,而在执行get方法在线程返回结果之前是阻塞的,jdk这对于想要异步的处理结果没有提供相应的接口,guava的ListenableFuture接口就是为实现异步的获取Future中的结果而出现的。
顾名思义,ListenableFuture是可监听的Future,可以在结果返回的时候以方法回调的方式实现异步的后续操作。那么如何获取ListenableFuture呢,方法有两种:
1. 将jdk提供的Futhure转换成ListenableFuture
2. 将ExcutorService线程池转换成ListeningExcutorService,继而获取ListenableFuture

第一种方式我们使用如下适配器获得Future对应的ListenableFuture

ListenableFuture<String> listenableFuture=JdkFutureAdapters.listenInPoolThread(future);

第二种方式我们使用一个线程池的修饰类获得

ListeningExecutorService listeningThreadPool=MoreExecutors.listeningDecorator(threadPool);
ListenableFuture<String> listenableFuture=listeningThreadPool.submit(new Callable<String>() {....}

在获取了ListenableFuture之后,我们同样有两种方式异步获取线程执行结果
1. 添加FutureCallback执行回调方法
2. 为ListenableFuture添加监听线程

第一种方法使用Futures的addCallback方法实现

Futures.addCallback(listenableFuture,new FutureCallback<String>(){

            @Override
            public void onSuccess(String result) {
                System.out.println(result);
            }

            @Override
            public void onFailure(Throwable t) {
                t.printStackTrace();
            }
        });

第二种方法不太推荐,使用listenableFuture.addListener的方法实现。

源码解读

我们看到guava的实现方式非常优雅,那么它是怎么实现这种异步回调的呢,以JdkFutureAdapters.listenInPoolThread为例,其实他是返回了一个ListenableFutureAdapter的内部类,它实现了ListenableFuture并且继承了ForwardingFuture类,然后调用callback的时候会新建一个Runable线程任务,其主要逻辑是使用Future的get方法阻塞获取执行结果,在结果完成的时候回到callback类的onSuccess方法,如果出现异常则调用onFailure方法。
整个方法的设计使用了适配器模式,ListenableFuture是最终用户需要的接口,ListenableFutureAdapter是适配器,ForwordingFuture实现了Future接口,是被适配者。

关于FutureTask

FutureTask是Future的一个实现类,它同时实现了Runable接口,直接使用线程池运行FutureTask,并且获取阻塞获取结果,其在异步方面并没有做出改变。

本节代码

所有测试代码获取可以点击这里
参考文献:guava并发深入学习 FutureTask

Java AIO中的Future和CompleteHandler

Socket通信是Java网络通信的一种方式,在基础的阻塞BIO后出现了NIO,NIO采用了多路复用思想,使得一个线程可以监听多个socket文件描述符,使得在在一次轮训的过程中可以查看多个阻塞IO的状态,相比BIO每次只能监听一个IO状态࿰

  • 1
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值