用CompletableFuture异步执行多个service,并获取service的返回值

巨大的建筑,总是由一木一石叠起来的,我们何妨做做这一木一石呢?我时常做些零碎事,就是为此。
这是对的,但是我没有说过这句话! —— 鲁迅

java8中增加了一个CompletableFuture,这是对Future的补充.
CompletableFutrue,主要是异步执行,目的的加快执行速度,用不同的线程去执行不同的逻辑,到最后再将得到的结果整合起来.
但是我试了各种的CompletableFuture的异步方法,最终都是同步执行.

用CompletableFuture.allof….join 进行异步触发

假如有多个completableFutrue,用他的allof方法,会异步执行.
以下用代码举例:

建立一个执行时间长的service

import java.text.SimpleDateFormat;
import java.util.Date;

public class MyService {

  private Long value;

  public MyService(Long value) {
    this.value = value;
  }

  public Long getValue() {
    try {
      Thread.sleep(2000);
    } catch (InterruptedException e) {
      e.printStackTrace();
    }
    System.out.println(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()) + " :myValue" + value);
    return value;
  }

}

调用方法

private void streamService() throws Exception{
    Long start = System.currentTimeMillis();
    Long sum = 0L;
    CompletableFuture[] collect = serviceList.stream()
        .map(service -> CompletableFuture.supplyAsync(service::getValue)).toArray(CompletableFuture[]::new);
    CompletableFuture.allOf(collect).join();
    for (CompletableFuture future : collect) {
      Long value = (Long)future.get();
      sum += value;
    }
    System.out.println(sum);
    Long end = System.currentTimeMillis();
    Long time = (end - start)/1000;
    System.out.println("using " + time);
  }
  1. serviceList是刚才的MyService的List,先将其转化为一个CompletableFuture的数组
  2. 用allOf.join执行
  3. 用每一个CompletableFuture的get来获取service的返回值

注意

直接对service进行 join 或 get,就直接阻塞了,等执行完了,才能运行到下一个service,不管用.
当allof.join之后,再进行get,此时已经执行完了,有值了,再get,速度回很快

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章