本文分两部分来介绍Executor:Executor的结构和Executor框架包含的成员组件java
一、Executor框架的结构编程
Executor主要由3大部分组成。小程序
1.一、任务。包含被执行任务须要实现的接口:Runnable接口或Callable接口。
服务器
1.二、任务的执行。包括任务执行机制的核心接口Executor,以及继承自Executor接口的ExecutorService接口。Executor有两个关键类实现了ExecutorService接口(ThreadPoolExecutor和ScheduledThreadPoolExecutor)
并发
1.三、异步计算的结果。包括接口Future和实现Future接口的FutureTask类。框架
下面是这些类和接口的简介。
异步
Executor是一个接口,它是Executor框架的基础,它将任务的提交和任务的执行分离开来。
spa
ThreadPoolExecutor是线程池的核心实现类,用来执行被提交的任务。
线程
ScheduledThreadPoolExecutor是一个实现类,能够在给定的延迟后运行命令,或者按期执行命令。SchduledThreadPoolExecutor比Timer更灵活,功能更强大。
code
Future接口和实现Future接口的FutureTask类,表明异步计算的结果
Runnable接口和Callable接口的实现类,均可以被ThreadPoolExecutor或SchduledThreadPoolExecutor执行
二、Executor框架的成员
介绍Executor框架的主要成员:ThreadPoolExecutor、ScheduledThreadPoolExecutor、Future接口、Runnable接口、Callable接口、Executors。
2.一、ThreadPoolExecutor
ThreadPoolExecutor一般使用工厂类Executors来建立,Executors能够建立3种类型的ThreadPoolExecutor:SingleThreadExecutor、FixThreadPool、CachedThreadPool。
下面分别介绍这3种ThreadPoolExecutor。
1)FixedThreadPool。下面是Executors提供的,建立使用固定线程数的FixedThreadPool的API
public static ExecutorService newFixedThreadPool(int nThreads) { return new ThreadPoolExecutor(nThreads, nThreads, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue<Runnable>()); }
public static ExecutorService newFixedThreadPool(int nThreads, ThreadFactory threadFactory) { return new ThreadPoolExecutor(nThreads, nThreads, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue<Runnable>(), threadFactory); }
FixedThreadPool适用于为了知足资源管理的需求,而须要限制当前线程数量的应用场景,它适用于负载比较重的服务器。
2)SingleThreadExecutor。下面是Executors提供的,建立使用单个线程的SingleThreadExecutor的API
public static ExecutorService newSingleThreadExecutor() { return new FinalizableDelegatedExecutorService (new ThreadPoolExecutor(1, 1, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue<Runnable>())); }
public static ExecutorService newSingleThreadExecutor(ThreadFactory threadFactory) { return new FinalizableDelegatedExecutorService (new ThreadPoolExecutor(1, 1, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue<Runnable>(), threadFactory)); }
SingleThreadExecutor适用于须要保证顺序执行各个任务;而且在任意时间点,不会有多个线程是活动着的应用场景。
3)CachedThreadPool。下面是Executors提供的,建立一个会根据须要而建立新线程的CachedThreadPool的API
public static ExecutorService newCachedThreadPool() { return new ThreadPoolExecutor(0, Integer.MAX_VALUE, 60L, TimeUnit.SECONDS, new SynchronousQueue<Runnable>()); }
public static ExecutorService newCachedThreadPool(ThreadFactory threadFactory) { return new ThreadPoolExecutor(0, Integer.MAX_VALUE, 60L, TimeUnit.SECONDS, new SynchronousQueue<Runnable>(), threadFactory); }
CachedThreadPool是大小无界的线程池,适用于执行不少短时间异步任务的小程序,或者是负载比较轻的服务器。
2.二、SchduledThreadPoolExecutor
SchduledThreadPoolExecutor一般使用工厂类Executors来建立,Executors能够建立2中类型的SchduledThreadPoolExecutor,以下:
SchduledThreadPoolExecutor。包含若干个线程的SchduledThreadPoolExecutor。
SingleThreadSchduledExecutor。只包含一个线程的SchduledThreadPoolExecutor。
1)SchduledThreadPoolExecutor。下面是Executors提供的,建立固定个数的线程SchduledThreadPoolExecutor的API。
public static ScheduledExecutorService newScheduledThreadPool(int corePoolSize) { return new ScheduledThreadPoolExecutor(corePoolSize); }
public static ScheduledExecutorService newScheduledThreadPool( int corePoolSize, ThreadFactory threadFactory) { return new ScheduledThreadPoolExecutor(corePoolSize, threadFactory); }
SchduledThreadPoolExecutor适用于须要多个后台线程执行的周期任务,同时为了知足资源管理的需求而须要限制后台线程数量的场景。
2)SingleThreadSchduledExecutor。下面是Executors提供的,建立单个线程的SingleThreadSchduledExecutor的API。
public static ScheduledExecutorService newSingleThreadScheduledExecutor() { return new DelegatedScheduledExecutorService (new ScheduledThreadPoolExecutor(1)); }
public static ScheduledExecutorService newSingleThreadScheduledExecutor(ThreadFactory threadFactory) { return new DelegatedScheduledExecutorService (new ScheduledThreadPoolExecutor(1, threadFactory)); }
SingleThreadSchduledExecutor适用于须要单个后台线程执行周期任务,同时须要保证顺序地执行各个任务的场景。
三、Future接口
Future接口和实现Future接口的FutureTask类用来表示异步计算的结果,当咱们把Runnable接口或者Callable接口的实现类提交(submit)给ThreadPoolExecutor或者SchduledThreadPoolExecutor时,ThreadPoolExecutor或者SchduledThreadPoolExecutor会向咱们返回一个FutureTask对象。下面是对应的API
public Future<?> submit(Runnable task) { return e.submit(task); } public <T> Future<T> submit(Callable<T> task) { return e.submit(task); } public <T> Future<T> submit(Runnable task, T result) { return e.submit(task, result); }
四、Runnable和Callable接口
Runnable和Callable接口的实现类均可以被hreadPoolExecutor或者SchduledThreadPoolExecutor执行。它们之间的区别是Runnable不会返回结果,而Callable能够返回结果。
除了能够自已建立实现Callable接口的对象外,还可使用工厂类Executors来把一个Runnable包装成一个Callable。
下面是Executors提供的,把一个Runnable包装成Callable的API
public static Callable<Object> callable(Runnable task) { if (task == null) throw new NullPointerException(); return new RunnableAdapter<Object>(task, null); }
下面是Executors提供的,把一个Runnable和一个待返回的结果包装成一个Callable的API
public static <T> Callable<T> callable(Runnable task, T result) { if (task == null) throw new NullPointerException(); return new RunnableAdapter<T>(task, result); }
当咱们把一个Callable对象提交给ThreadPoolExecutor或者SchduledThreadPoolExecutor执行时,summit()会向咱们返回一个FutureTask对象。咱们能够执行FutureTask.get()来等待任务执行完成。当任务完成后FutureTask.get()将会返回任务的结果。
注明:好记性不如烂笔头,以上内容来自《Java并发编程的艺术》