如果对线程池不太了解请看《Thread线程系列之线程池介绍API的简介》与《Thread线程系列之线程池详解》
CompletionService与ExecutorService都是属于线程池,都具备执行多线程的能力。但CompletionService执行多线程多任务时,那个任务优先执行完成,就会优先返回得到这个优先执行完任务的结果,以此类推。而ExecutorService执行多线程多任务时,是在当所有任务执行完之后,再一并返回结果。
看示例:
先看公共的任务类:
MyTask类:传递参数时间,且任务停顿相应的参数时间,再返回时间数;
public class MyTask implements Callable<Integer> {
private Integer time;
public MyTask(Integer time) {
this.time = time;
}
@Override
public Integer call() throws Exception {
Thread.sleep(time); //暂停time秒
return time; //返回time值
}
}
数据定义:多任务集合
//多任务集合myTaskList
private static List<MyTask> getMyTaskList(){
List<MyTask> myTaskList = new ArrayList<>();
MyTask myTask1 = new MyTask(6 * 1000);
MyTask myTask2 = new MyTask(3 * 1000);
MyTask myTask3 = new MyTask(8 * 1000);
MyTask myTask4 = new MyTask(1000);
MyTask myTask5 = new MyTask(4 * 1000);
myTaskList.add(myTask1);
myTaskList.add(myTask2);
myTaskList.add(myTask3);
myTaskList.add(myTask4);
myTaskList.add(myTask5);
return myTaskList;
}
1.看线程池(缓存型线程池)进行多任务执行的示例以及效果
private static final SimpleDateFormat sdf = new SimpleDateFormat("HH:mm:ss");
private static final ExecutorService executorService = Executors.newCachedThreadPool();
public static void main(String[] args) {
long startTime = System.currentTimeMillis();
testExecutorService(getMyTaskList());//缓存型线程池执行任务
long endTime = System.currentTimeMillis();
System.out.println("运行时间:" + (endTime - startTime)+"毫秒");
}
private static void testExecutorService(List<MyTask> myTaskList) {
List<Future<Integer>> futureList = new ArrayList<>();
for (MyTask myTask : myTaskList) {
futureList.add(executorService.submit(myTask));
}
try {
for (Future<Integer> future : futureList) {
Integer result = future.get();
System.out.println("结果\t"+sdf.format(new Date())+"\t"+result+"毫秒");
}
} catch (InterruptedException | ExecutionException e) {
e.printStackTrace();
}finally {
executorService.shutdown();
}
}
执行结果:(注意:开始运行时间与每个任务得到结果的时间的时间差【区别与CompletionService执行的结果】)
开始运行时间 18:35:27
结果 18:35:33 6000毫秒
结果 18:35:33 3000毫秒
结果 18:35:35 8000毫秒
结果 18:35:35 1000毫秒
结果 18:35:35 4000毫秒
运行时间:8048毫秒
2.看CompletionService进行多任务执行的示例以及效果
private static final SimpleDateFormat sdf = new SimpleDateFormat("HH:mm:ss");
private static final ExecutorService executorService = Executors.newCachedThreadPool();
private static final CompletionService<Integer> completionService = new ExecutorCompletionService<>(executorService);
public static void main(String[] args) {
System.out.println("开始运行时间\t"+sdf.format(new Date()));
long startTime = System.currentTimeMillis();
testCompletionService(getMyTaskList());//缓存型线程池执行任务
long endTime = System.currentTimeMillis();
System.out.println("运行时间:" + (endTime - startTime)+"毫秒");
}
private static void testCompletionService(List<MyTask> myTaskList) {
for (MyTask myTask : myTaskList) {
completionService.submit(myTask);
}
try {
for (int i = 0; i < myTaskList.size(); i++) {
Future<Integer> take = completionService.take();
Integer result = take.get();
System.out.println("结果\t"+sdf.format(new Date())+"\t"+result+"毫秒");
}
} catch (InterruptedException | ExecutionException e) {
e.printStackTrace();
}finally {
executorService.shutdown();
}
}
执行结果:(注意:开始运行时间与每个任务得到结果的时间的时间差【区别与ExecutorService执行的结果】)
开始运行时间 18:33:57
结果 18:33:58 1000毫秒
结果 18:34:00 3000毫秒
结果 18:34:01 4000毫秒
结果 18:34:03 6000毫秒
结果 18:34:05 8000毫秒
运行时间:8009毫秒