转自:https://blog.csdn.net/jdsjlzx/article/details/52912701

FutureTask既是Future、Runnable,又是包装了Callable(如果是Runnable最终也会被转换为Callable ), 它是这两者的合体。

package io.renren.test2;

import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.*; public class test2 { public static void main(String[] args) throws ExecutionException, InterruptedException {
testFuture();
// testCompletionService();
} //结果的输出和线程的放入顺序 有关(如果前面的没完成,就算后面的哪个完成了也得等到你的牌号才能输出!),so阻塞耗时
public static void testFuture() throws InterruptedException, ExecutionException {
System.out.println("--1.1--> main Thread begin:");
ExecutorService executor = Executors.newCachedThreadPool();
List<Future<String>> result = new ArrayList<Future<String>>();
for (int i = 0; i < 10; i++) {
Future<String> submit = executor.submit(new Task(i));
result.add(submit);
}
executor.shutdown();
for (int i = 0; i < 10; i++) {//一个一个等待返回结果
System.out.println("--1.2--> 一个一个等待返回结果: " + result.get(i).get());
}
System.out.println("--1.3--> main Thread end:");
} //结果的输出和线程的放入顺序 无关(谁完成了谁就先输出!主线程总是能够拿到最先完成的任务的返回值,而不管它们加入线程池的顺序),so很大大缩短等待时间
private static void testCompletionService() throws InterruptedException, ExecutionException {
System.out.println("--2.2--> main Thread begin:");
ExecutorService executor = Executors.newCachedThreadPool();
ExecutorCompletionService<String> completionService = new ExecutorCompletionService<>(executor);
for (int i = 0; i < 10; i++) {
completionService.submit(new Task(i));
}
executor.shutdown();
for (int i = 0; i < 10; i++) {
// 检索并移除表示下一个已完成任务的 Future,如果目前不存在这样的任务,则等待。
Future<String> future = completionService.take(); //这一行没有完成的任务就阻塞
System.out.println("--2.3--> " + future.get()); // 这一行在这里不会阻塞,引入放入队列中的都是已经完成的任务
}
System.out.println("--2.4--> main Thread end:");
} private static class Task implements Callable<String> { private volatile int i; public Task(int i) {
this.i = i;
} @Override
public String call() throws Exception {
Thread.sleep(1000);
System.out.println(Thread.currentThread().getName());
return "--0.1--> 任务 : " + i;
} }
}
testFuture() 打印:
--1.1--> main Thread begin:
pool-1-thread-9
pool-1-thread-2
pool-1-thread-1
pool-1-thread-3
pool-1-thread-6
pool-1-thread-7
pool-1-thread-5
pool-1-thread-8
pool-1-thread-4
--1.2--> 一个一个等待返回结果: --0.1--> 任务 : 0
--1.2--> 一个一个等待返回结果: --0.1--> 任务 : 1
--1.2--> 一个一个等待返回结果: --0.1--> 任务 : 2
--1.2--> 一个一个等待返回结果: --0.1--> 任务 : 3
--1.2--> 一个一个等待返回结果: --0.1--> 任务 : 4
--1.2--> 一个一个等待返回结果: --0.1--> 任务 : 5
--1.2--> 一个一个等待返回结果: --0.1--> 任务 : 6
--1.2--> 一个一个等待返回结果: --0.1--> 任务 : 7
--1.2--> 一个一个等待返回结果: --0.1--> 任务 : 8
pool-1-thread-10
--1.2--> 一个一个等待返回结果: --0.1--> 任务 : 9
--1.3--> main Thread end:
testCompletionService() 打印:
--2.2--> main Thread begin:
pool-1-thread-1
--2.3--> --0.1--> 任务 : 0
pool-1-thread-2
pool-1-thread-7
--2.3--> --0.1--> 任务 : 1
--2.3--> --0.1--> 任务 : 6
pool-1-thread-3
--2.3--> --0.1--> 任务 : 2
pool-1-thread-8
--2.3--> --0.1--> 任务 : 7
pool-1-thread-9
--2.3--> --0.1--> 任务 : 8
pool-1-thread-6
pool-1-thread-5
pool-1-thread-4
--2.3--> --0.1--> 任务 : 5
--2.3--> --0.1--> 任务 : 4
--2.3--> --0.1--> 任务 : 3
pool-1-thread-10
--2.3--> --0.1--> 任务 : 9
--2.4--> main Thread end:

CompletionService的好处与使用场景的更多相关文章

  1. Java批处理ExecutorService/CompletionService

    服务端接收一个请求,常常需要同时进行几个计算或者向其他服务发送请求,最后拼装结果返回上游.本文就来看下JDK提供几个并行处理方案,牵涉到ExcecutorService/CompletionServi ...

  2. [ZZ] Maxwell 架构

    http://digi.163.com/14/0218/23/9LDCTFON00162DSP.html [IT168 评测]随着一句“娘娘,封神啦(宝鸡口音)”,中国的观众迅速认识到了两个极其出彩的 ...

  3. Activiti工作流学习-----基于5.19.0版本(5)

    五.与Spring集成 实际项目中一般都有Spring的身影,与Spring集成使得Activiti的实用性得到提高.activiti和Spring整合需要activiti-spring的jar在类路 ...

  4. 图解Javascript——作用域、作用域链、闭包

    什么是作用域? 作用域是一种规则,在代码编译阶段就确定了,规定了变量与函数的可被访问的范围.全局变量拥有全局作用域,局部变量则拥有局部作用域. js是一种没有块级作用域的语言(包括if.for等语句的 ...

  5. jquery源码 Callback

    工具方法.对函数的统一管理. jquery2.0.3版本$.Callback()部分的源码如下: // String to Object options format cache var option ...

  6. js 作用域,作用域链,闭包

    什么是作用域? 作用域是一种规则,在代码编译阶段就确定了,规定了变量与函数的可被访问的范围.全局变量拥有全局作用域,局部变量则拥有局部作用域. js是一种没有块级作用域的语言(包括if.for等语句的 ...

  7. Docke--Dockerfile指令介绍

    Dockerfile 构建镜像常用指令 Dockerfile 是一个文本文件,其内包含了一条条的指定(Instruction),每一条指令构建一层,因此每一条指定的内容,就是描述该层应当如何构建. 通 ...

  8. pyqtgraph

    安装  pip3 install pyqtgraph 在PyQtGraph中,有几种绘制图形的方法: pyqtgraph.plot():创建一个新的绘图窗口来显示数据: PlotWidget.plot ...

  9. java异步编程降低延迟

    目录 java异步编程降低延迟 一.ExecutorService和CompletionService 二.CompletableFuture(重要) 三.stream中的parallel(并行流) ...

随机推荐

  1. ionic -v2版本项目结构

    myApp │  config.xml  //项目配置文件,包名.名称.minSdkVersion等都在此处配置 │  ionic.config.json │  package.json  //项目依 ...

  2. Android Studio 于夜神模拟器进行连接

    本文使用夜神模拟器自带的nox_adb.exe在Android Studio中连接夜神模拟器. 1.在夜神模拟器的安装路径下,在bin文件夹下有个nox_adb.exe文件,复制黄色框路径如图: 2. ...

  3. Docker实战部署应用——Tomcat

    Tomcat 部署 拉取tomcat镜像 docker pull tomcat:8 创建tomcat容器 创建tomcat容器用于 Web应用,并且进行目录映射 docker run -id --na ...

  4. CreateProcessAsUser 服务调用

    CreateProcessAsUser 函数 如果想通过服务向桌面用户Session 创建一个复杂UI 程序界面,则需要使用CreateProcessAsUser 函数为用户创建一个新进程用来运行相应 ...

  5. sed \s

    export m1=`free|cut -d ":" -f2|sed -e "s/^\s\s*//g"|head -2|tail -1|cut -d ' ' - ...

  6. libopencv_imgcodecs3.so.3.3.1: undefined reference to `TIFFReadDirectory@LIBTIFF_4.0

    ubundu 编译 C++工程时遇到的: 解决方案: https://blog.csdn.net/qq_29572513/article/details/88742652

  7. OC + RAC (九) 过滤

    // 跳跃 : 如下,skip传入2 跳过前面两个值 // 实际用处: 在实际开发中比如 后台返回的数据前面几个没用,我们想跳跃过去,便可以用skip - (void)skip { RACSubjec ...

  8. Windows系统安装教程

    身边很多朋友电脑系统因为这样那样的问题不能开机,需要重装系统,但是又不知道从何下手.很不建议去电脑店重装系统,因为电脑店用的操作系统很多都有捆绑软件和主页捆绑,对电脑体验影响很坏.这篇教程只是针对新手 ...

  9. GEI步态能量图生成

    步态能量图生成主要有两步,主要为: 在原始轮廓图上对人的轮廓进行裁剪,在下面制作步态能量图图片叠加以什么为中心位置也是一个问题.一般有两种方式,一种是中心位置为人体宽的一半.另一种是以头顶为中心位置. ...

  10. 向量积&&凸包算法

    参考:Thanks 百度百科 http://blog.csdn.net/keng_s/article/details/52131034 https://www.cnblogs.com/aiguona/ ...