深入理解并发编程-FutureTask

本文为读书笔记
可参考:FutureTask jdk8实现
JKD1.8不再依赖AQS来实现,而是用的CAS+state

1. FutureTask简介

Future接口和实现Future接口的FutureTask类,代表异步计算的结果。

此任务的运行状态,最初是新的。运行状态只有在方法集中才会过渡到终端状态, setException和cancel。在完成期间,state可能会承担暂态值的完成(而结果正在被设置)或中断(仅在中断跑步者以满足a时)取消(真))。从这些中间过渡到最终状态使用更便宜的有序/惰性写,因为值是唯一的无法进一步修改。

  • Possible state transitions:
    • NEW -> COMPLETING -> NORMAL
    • NEW -> COMPLETING -> EXCEPTIONAL
    • NEW -> CANCELLED
    • NEW -> INTERRUPTING -> INTERRUPTED
//注意关键字state
	private volatile int state;
    private static final int NEW          = 0;
    private static final int COMPLETING   = 1;
    private static final int NORMAL       = 2;
    private static final int EXCEPTIONAL  = 3;
    private static final int CANCELLED    = 4;
    private static final int INTERRUPTING = 5;
    private static final int INTERRUPTED  = 6;

根据FutureTask.run()方法被执行的时机,FutureTask可以处于下面3种状态。

1)未启动。FutureTask.run()方法还没有被执行之前,FutureTask处于未启动状态。当创建一个FutureTask,且没有执行FutureTask.run()方法之前,这个FutureTask处于未启动状态。
2)已启动。FutureTask.run()方法被执行的过程中,FutureTask处于已启动状态。
3)已完成。FutureTask.run()方法执行完后正常结束,或被取消(FutureTask.cancel(…)),或执行FutureTask.run()方法时抛出异常而异常结束,FutureTask处于已完成状态。

状态跃迁图

在这里插入图片描述

2. FutureTask的使用

可以把FutureTask交给Executor执行;也可以通过ExecutorService.submit(…)方法返回一个FutureTask,然后执行FutureTask.get()方法或FutureTask.cancel(…)方法。除此以外,还可以单独使用FutureTask。
在这里插入图片描述

当一个线程需要等待另一个线程把某个任务执行完后它才能继续执行,此时可以使用FutureTask。
假设有多个线程执行若干任务,每个任务最多只能被执行一次。当多个线程试图同时执行同一个任务时,只允许一个线程执行任务,其他线程需要等待这个任务执行完后才能继续执行。

部分核心方法:
在这里插入图片描述

3. FutureTask的实现(JKD1.8不再依赖AQS来实现)

文章应该是1.8以前:
FutureTask的 实 现 基 于AbstractQueuedSynchronizer(以 下 简 称 为AQS)。
设计示意图:
在这里插入图片描述

4. 使用举例

  public static void main(String[] args) {
        Callable<Integer> call = new Callable<Integer>() {

            @Override
            public Integer call() throws Exception {
                return 1;
            }
        };

        FutureTask<Integer> task = new FutureTask<>(call);
        //交给Thread执行
        Thread thread = new Thread(task);
        thread.start();
        

        Integer result = null;
        try {
            result = task.get();
        } catch (InterruptedException e) {
            e.printStackTrace();
        } catch (ExecutionException e) {
            e.printStackTrace();
        }

        System.out.println("结果为:" + result);

    }
 public static void main(String[] args) throws ExecutionException, InterruptedException {

        ExecutorService executorService = Executors.newSingleThreadExecutor();
        C c = new C();
        FutureTask futureTask = new FutureTask<>(c);
        executorService.execute(futureTask);
        System.out.println(futureTask.get());
        executorService.shutdownNow();
    }
    class C implements Callable {

    @Override
    public Object call() throws Exception {
        return 1;
    }
}

或者

   Future submit = executorService.submit(c);
        System.out.println(submit.get());
        executorService.shutdownNow();
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值