【并发编程】- 线程池执行Callable任务获取返回值

Callable、Future使用

针对线程Thread对象不具有返回值的功能,但是有请求需要线程返回值,所以需要用到Callable和Future来让线程具有返回值的功能。
Callable接口与线程密不可分,但是和Runnable有以下主要的区别是

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

Callable接口的call()方法可以声明抛出异常,而Runnable接口的run()方法不可以声明抛出异常。
执行完Callable接口中的任务后,返回值是通过Future接口进行获取。

ThreadPoolExecutor使用submit提交Callable的任务

线程执行代码如下:

public class TheCallable implements Callable<String> {
    private int number;

    public TheCallable(int number){
        super();
        this.number=number;
    }

    @Override
    public String call() throws Exception {
        Thread.sleep(5000);
        return "返回值:"+number;
    }
}

运行类代码如下:

@Slf4j
public class CallableRun {
    public static void main(String[] args) {
        TheCallable theCallable = new TheCallable(18);
        ThreadPoolExecutor threadPoolExecutor = new ThreadPoolExecutor(2, 3, 10, TimeUnit.SECONDS, new LinkedBlockingQueue<>());
        Future<String> future = threadPoolExecutor.submit(theCallable);
        try {
            log.info("开始时间:{}",System.currentTimeMillis());
            log.info("线程 "+future.get());
            log.info("结束时间:{}",System.currentTimeMillis());
        } catch (InterruptedException e) {
            e.printStackTrace();
        } catch (ExecutionException e) {
            e.printStackTrace();
        }

    }
}

运行结果如下:

17:09:57.944 [main] INFO com.ozx.concurrentprogram.executor.controller.CallableRun - 开始时间:1659344997940
17:10:02.942 [main] INFO com.ozx.concurrentprogram.executor.controller.CallableRun - 线程 返回值:18
17:10:02.943 [main] INFO com.ozx.concurrentprogram.executor.controller.CallableRun - 结束时间:1659345002943

从运行结果看出future调用get()是阻塞的,get()方法具有阻塞特性。
ExecutorService使用submit提交Runnable任务
方法submit()可以传入Callable对象,也可以传入Runnable对象,说明submit()方法支持有返回值和无返回值的功能。
运行类代码如下:

@Slf4j
public class RunnableRun {
    public static void main(String[] args) {
        Runnable runnable = new Runnable() {
            @Override
            public void run() {
 SimpleDateFormat simpleDateFormat = new SimpleDateFormat("HH:mm:ss");
                log.info("Runnable 输出的内容:{}",simpleDateFormat.format(new Date()));
            }
        };

        ExecutorService executorService = Executors.newCachedThreadPool();
        Future future = executorService.submit(runnable);
        try {
            log.info("任务返回值:{},执行isDone方法结果:{}",future.get(),future.isDone());
        } catch (InterruptedException e) {
            e.printStackTrace();
        } catch (ExecutionException e) {
            e.printStackTrace();
        }

    }
}

运行结果如下:

17:31:37.704 [pool-1-thread-1] INFO com.ozx.concurrentprogram.executor.controller.RunnableRun - Runnable 输出的内容:17:31:37
17:31:37.715 [main] INFO com.ozx.concurrentprogram.executor.controller.RunnableRun - 任务返回值:null,执行isDone方法结果:true

从运行结果看出submit()方法传入Callable接口则有返回值,但是传入Runnable则无返回值,执行任务的返回值为null,之前验证过方法get()是具有阻塞特性,而isDone()方法是无阻塞特性。

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值