线程(十)关于Callable和future的介绍:

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/u014252478/article/details/83586221

1、Callable类似于Runnable,为线程设计。区别在于,callable有返回值future,而Runnable则不会有返回值,同时Runnable不会抛出异常。future用于记录线程是否完成,不能用于判断线程执行是否正确。

关于callable实例:

public class CallableAndFuture {

    public static void main(String[] args) {
        ExecutorService threadPool = Executors.newSingleThreadExecutor();// 创建一个线程即可
        Future<String> future = threadPool.submit(
                new Callable<String>() {

                    @Override
                    public String call() throws Exception {
                        Thread.sleep(2000);
                        return "hello";
                    }
                }   
            );
        System.out.println("等待结果:");
        try {
            System.out.println("拿到结果:" + future.get());
        } catch (Exception e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } 
}

关于产生future,还有


private ScheduledExecutorService pool = Executors.newScheduledThreadPool(3);
​
    SimpleDateFormat formatter = new SimpleDateFormat("yyyy-MM-dd  HH:mm:ss");  //没有精确到毫秒
​
    public  void scheduledStatusNotify() {
        ScheduledFuture<?> future = pool.scheduleWithFixedDelay(new Runnable() {
            @Override
            public void run() {
            ..........
           }
      });
    }

2、在起多个线程的时候,可以将线程池扔进CompletionService<T>接口中,当需要查看多个返回值结果时,可以从当中取出来:

public class CallableAndFuture {

    public static void main(String[] args) {

        ExecutorService threadPool = Executors.newCachedThreadPool();//定义一个缓存线程池
        CompletionService<Integer> completionService = 
                new ExecutorCompletionService<Integer>(threadPool); //将线程池扔进去
        for(int i = 1; i <= 5; i ++) {
            final int seq = i;
            completionService.submit( //用里面装的线程去执行这些任务,每个线程都会返回一个数据
                    new Callable<Integer> () {

                        @Override
                        public Integer call() throws Exception {
                            Thread.sleep(new Random().nextInt(5000));
                            return seq;
                        }

                    }
                );
        }
        for(int i = 0; i < 5; i ++) { //执行完了后,再取出来
            try {
                System.out.print(completionService.take().get() + " ");
            } catch (Exception e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            } 
        }
    }   
}

ExecutorCompletionService的实现相当直观。它在构造函数中创建一个BlockingQueue,用它去保持完成的结果。 计算完成时会调用FutureTask中的done方法。

当提交一个任务后,首先把这个任务包装为一个QueueingFuture,它是 FutureTask的一个子类,然后覆写done方法,将结果置入BlockingQueue中,take和poll方法委托给了 BlockingQueue,它会在结果不可用时阻塞。

猜你喜欢

转载自blog.csdn.net/u014252478/article/details/83586221