默认情况下,线程Thread对象不具有返回值的功能,如果在需要取得返回值的情况下会极为不方便。jdk1.5中可以使用Future 和 Callable 来获取线程返回值

Callable 可以 看成与 Runnable 一样的但是有返回值的接口。

Callable接口的call()方法有返回值,而Runnable接口的run方法没有返回值;

Callable接口的call()方法可以声明抛出异常,而Runnable接口的run方法不可以声明抛出异常。

执行完Callable接口中的任务后,返回值是通过Future接口进行获取的。

看例子:

     final SimpleDateFormat sf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss.SSS");
ExecutorService executorService = Executors.newCachedThreadPool();
// ExecutorService executorService = Executors.newFixedThreadPool(3);
List<Future<String>> futureList = new ArrayList<Future<String>>();
// 此线程池运行5个线程
for (int i = 0; i < 5; i++) {
final int index = i;
// 使用 submit 方法 和 execute 方法的区别是,execute 方法没有返回值,而 submit 方法有返回值。
Future<String> future = executorService.submit(new Callable<String>() {
@Override
public String call() throws Exception {
System.out.println("Thread-" + index + "-begin-" + sf.format(new Date()));
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("Thread-" + index + "-end-" + sf.format(new Date()));
return "index-" + index;
} });
futureList.add(future);
}
// future.get() 是阻塞执行的,所以获取值要在线程都启动之后,再获取
for (Future<String> future : futureList) {
try {
System.out.println(future.get()); // 获取线程返回值
} catch (InterruptedException e) {
e.printStackTrace();
} catch (ExecutionException e) {
e.printStackTrace();
}
}

ExecutorService 的 submit 方法 和 execute 方法的区别是,

  execute 方法没有返回值,不能直接捕获异常,但可以通过自定义ThreadFactory的方式捕获异常;

  submit 方法有返回值,可以直接使用 catch Execution-Exception捕获异常。

Future 的常用api:

get()    获取线程返回值,阻塞执行

get(long timeout, TimeUnit unit)    获取线程返回值(有超时时间),阻塞执行
cancel(boolean mayInterruptIfRunning)    取消执行,入参为true表示,如果线程正在运行则中断执行;为false表示,如果线程没有在运行才中断继续执行;返回值表示取消执行命令是否成功完成
isCancelled()    是否已取消执行
isDone()    如果完成此任务,则返回true。完成可能是由于正常终止、异常或取消——在所有这些情况下,此方法将返回true。

【Java并发核心五】Future 和 Callable的更多相关文章

  1. 【Java并发核心三】CountDownLatch、CyclicBarrier及Phaser

    个人感觉,看书学习还是需要“不求甚解”,因为一旦太过于计较小的得失,就容易钻牛角尖,学习进度也慢.我们完全可以先学一个大概,等到真正用到的时候再把那些细节丰富起来,就更有针对性. 所以,针对java并 ...

  2. 和朱晔一起复习Java并发(五):并发容器和同步器

    本节我们先会来复习一下java.util.concurrent下面的一些并发容器,然后再会来简单看一下各种同步器. ConcurrentHashMap和ConcurrentSkipListMap的性能 ...

  3. Java并发机制(9)--Callable、Future、FutureTask的使用

    Java并发编程:Callable.Future.FutureTask的使用 整理自:博客园-海子-http://www.cnblogs.com/dolphin0520/p/3949310.html ...

  4. 【java并发核心一】Semaphore 的使用思路

    最近在看一本书<Java并发编程 核心方法与框架>,打算一边学习一边把学习的经验记下来,所粘贴的代码都是我运行过的,大家一起学习,欢迎吐槽. 估计也没多少人看我的博客,哈哈,那么我还是会记 ...

  5. Java并发(五):synchronized实现原理

    一.synchronized用法 Java中的同步块用synchronized标记. 同步块在Java中是同步在某个对象上(监视器对象). 所有同步在一个对象上的同步块在同时只能被一个线程进入并执行操 ...

  6. 【Java并发编程五】信号量

    一.概述 技术信号量用来控制能够同时访问某特定资源的活动的数量,或者同时执行某一给定操作的数据.计数信号量可以用来实现资源池或者给一个容器限定边界. 信号量维护了一个许可集,许可的初始量通过构造函数传 ...

  7. 【Java并发核心七】计划任务ScheduleExecutorService

    Java中定时任务Timer工具类提供了计划任务的实现,但是Timer工具类是以队列的方式来管理线程的,并不是以线程池的方式,这样在高并发的情况下,运行效率会有点低. ScheduleExecutor ...

  8. 【Java并发核心九】并发集合框架

    1.List接口:ArrayList 和 Vector ArrayList不是线程安全的,Vector是线程安全的,Vector有一个子类,可实现后进先出(LIFO)的对象堆栈(LinkedList ...

  9. Java并发(五)线程池使用番外-分析RejectedExecutionException异常

    目录 一.入门示例 二.异常场景1 三.异常场景2 四.解决方法 之前在使用线程池的时候,出现了 java.util.concurrent.RejectedExecutionException ,原因 ...

随机推荐

  1. JS结合a标签的使用

    a标签可以当作按钮使用,也可以当作连接. <a href=javascript:test(5)>弹出5</a>    会直接调用JS函数(注意中间没引号) <a href ...

  2. Java注解之Retention、Documented、Target、Inherited介绍

    先看代码,后面一个个来解析: @Retention(RetentionPolicy.RUNTIME) @Target(value = {ElementType.METHOD, ElementType. ...

  3. Eclipse中项目不会自动编译问题的坑和注意点

    最近接受了几个又小有老的项目,用eclipse反而比idea方便,但是好长时间不用eclipse了,还有有些问题的! 主要是碰到了classnotfound这个难缠的问题:这里记录一下几个坑,避免以后 ...

  4. Window和document的区别

    1.window 窗口对象.就是可视化区域的大小,不包含滚动条内东东. 2.document 对象,包含滚动条以外的区域

  5. 转载 - CNN感受野(receptive-fields)RF

    本文翻译自A guide to receptive field arithmetic for Convolutional Neural Networks(可能需要FQ才能访问),方便自己学习和参考.若 ...

  6. 利用autocomplete.js实现仿百度搜索效果(ajax动态获取后端[C#]数据)

    实现功能描述: 1.实现搜索框的智能提示 2.第二次浏览器缓存结果 3.实现仿百度搜索 <!DOCTYPE html> <html xmlns="http://www.w3 ...

  7. 实现自己的Koa2

    这部分的代码在https://github.com/zhaobao1830/koa2中demo文件夹中 Koa就是基于node自带的http模块,经过封装,监听端口,实现ctx(上下文)管理,中间件管 ...

  8. MVC,MVP和MVVM的区别

     MVC   转载标名出处  dub 从这幅图可以看到,我们可以看到在MVC里,View是可以直接访问Model的!从而,View里会包含Model信息,不可避免的还要包括一些业务逻辑. 在MVC模型 ...

  9. 最全的基于MFC的ActiveX控件开发教程

    浏览器插件之ActiveX开发(一) 一般的Web应用对于浏览器插件能不使用的建议尽量不使用,因为其涉及到安全问题以及影响用户安装(或自动下载注册安装)体验问题.在有特殊需求(如涉及数据安全的金融业务 ...

  10. CentOS切换为iptables防火墙并进行相关配置

    CentOS切换为iptables防火墙 切换到iptables首先应该关掉默认的firewalld,然后安装iptables服务. 1.关闭firewall: service firewalld s ...