首页 > 技术文章 > java 多线程 Future callable

wei-lai 2017-01-12 11:32 原文

面向对象5大设计原则

1.单一职责原则  一个类只包含它相关的方法,增删改查。一个方法只包含单一的功能,增加。一个类最多包含10个方法,一个方法最多50行,一个类最多500行。重复的代码进行封装,Don't Repeat Youself。

2.开放-封闭原则  类的设计对读取开放,对修改关闭。

3.里氏转换原则  子类可以转换成父类,父类可以强制转换成(转换成父类的)子类。

4.依赖倒置原则 类似于IOC 容器

5.接口隔离原则 暂时不知道。

参考链接:http://www.cnblogs.com/peijihui/archive/2012/04/07/2436127.html

-----------------------------------------------------------------------------------------------

Futrue的功能:子线程完成后 通知主线程。

 

public class CallableAndFuture {

    /**
     * @param args
     */
    public static void main(String[] args) {
        ExecutorService threadPool =  Executors.newSingleThreadExecutor();
        Future<String> future =
            threadPool.submit(
                new Callable<String>() {
                    public String call() throws Exception {
                        Thread.sleep(2000);
                        return "hello";
                    };
                }
        );
        System.out.println("等待结果");
        try {
            System.out.println("拿到结果:" + future.get()); //阻塞主线程
        } catch (InterruptedException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (Exception e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        
       
    }
    

}

 

futrue.get()其实阻塞了主线程,主线程会调用get方法获取结果,没有结果则等待。我在主线程中写一个方法也是等待,所以为什么要开子线程,为什么用future?

答:1.异步计算 (主线程计算10次==10个子线程计算一次)

http://jiangwenfeng762.iteye.com/blog/1325175

根据分而治之的思想,我们可以把异步计算的线程按照职责分为3类:

1. 异步计算的发起线程(控制线程):负责异步计算任务的分解和发起,把分解好的任务交给异步计算的work线程去执行,发起异步计算后,发起线程可以获得Futrue的集合,从而可以跟踪异步计算结果

2. 异步计算work线程:负责具体的计算任务

3. 异步计算结果收集线程:从发起线程那里获得Future的集合,并负责监控Future的状态,根据Future的状态来处理异步计算的结果。

 

/**
 * Futrue的应用场景
 * 
 * @author  
 *
 */
public class CallableAndFuture_My {

    // 异步计算
    public static class Task implements Callable<Integer> {

        @Override
        public Integer call() throws Exception {
           // System.out.println(Thread.currentThread().getName()+ " : executor!!!");
              Random random=new Random();
              int i=random.nextInt(10);
            System.out.println(Thread.currentThread().getName()+" : "+ i);
            return  i;
        }

    }

    public static void main(String[] args) {
        List<Future<Integer>> results = new ArrayList<Future<Integer>>();
        ExecutorService executorService = Executors.newCachedThreadPool();
        for (int i = 0; i < 30; i++) {
            results.add(executorService.submit(new Task()));
        }
        System.out.println("main waiting!");
        int count=0;
        for (Future<Integer> future : results) {
            try { 
                count+=future.get();
            } catch (InterruptedException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            } catch (ExecutionException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
        }
        
       System.out.println("main complete : "+count);
        if (!executorService.isShutdown()) {
            executorService.shutdown();
        }

    }
}

 

    2.多线程协作,比如菲波拉切数列,1,1,2,3,5,8... 后者需要前者的结果,就需要callable接口了,Future登场
http://blog.csdn.net/dabing69221/article/details/17595031

 

推荐阅读