先说一下线程池的好处,为什么要用线程池:
1.免去线程创建和销毁带来的性能开销,达到线程复用的效果。
2.能有效的控制线程池的最大并发数,避免大量的线程之间因互相抢占系统资源而导致的阻塞现象。
3.能够对线程进行简单的管理,并提供定时执行以及指定间隔循环执行等功能。
线程池的相关源码在 java.util.concurrent;下面
Android中的线程池都是通过配置 ThreadPoolExecutor来实现的,所以我们看一看这个类就行了,取自JDK 1.8
interface Executor
interface ExecutorService extends Executor
abstract class AbstractExecutorService implements ExecutorService
class ThreadPoolExecutor extends AbstractExecutorService
先看看Executor
执行线程请求,可能新开线程,可能复用池内已有线程
void execute(Runnable command);
再看看ExecutorService
//在shutdown队列中进行该操作,不会等待该task执行完毕
void shutdown();
//关闭所有正在执行的task并返回列表
List<Runnable> shutdownNow();
//字面意思boolean isShutdown();
//判断shut down队列是否已经全部执行了boolean isTerminated();
//同shutdown()方法 但是会等待当前task执行完毕boolean awaitTermination(long timeout, TimeUnit unit) throws InterruptedException;//立即执行该task<T> Future<T> submit(Callable<T> task);//添加到队列并返回结果<T> Future<T> submit(Runnable task, T result);//同上Future<?> submit(Runnable task);
//添加多个task,执行完毕后返回状态和结果<T> List<Future<T>> invokeAll(Collection<? extends Callable<T>> tasks) throws InterruptedException;//同上,加入了超时时间<T> List<Future<T>> invokeAll(Collection<? extends Callable<T>> tasks, long timeout, TimeUnit unit) throws InterruptedException;//加入多个task,返回执行成功的某个task的结果<T> T invokeAny(Collection<? extends Callable<T>> tasks) throws InterruptedException, ExecutionException;//同上,加入了超时时间<T> T invokeAny(Collection<? extends Callable<T>> tasks, long timeout, TimeUnit unit) throws InterruptedException, ExecutionException, TimeoutException;AbstractExecutorService是一个抽象类,实现了具体的方法,暂时不看。
最后看看和我们关系密切的ThreadPoolExecutor看一下他的构造方法public ThreadPoolExecutor(int corePoolSize, int maximumPoolSize, long keepAliveTime, TimeUnit unit, BlockingQueue<Runnable> workQueue, ThreadFactory threadFactory, RejectedExecutionHandler handler)一个个解释一下这几个形参的含义corePoolSize:线程池的核心线程数,一般情况下核心线程会在线程池中一直存活,当设置poolExecutor.allowCoreThreadTimeOut(),核心线程会根据keepAliveTime超时停止。maximumPoolSize:线程池的容量,当活动线程数达到这个数值后,后续的新任务将会被阻塞。keepAliveTime:非核心线程闲置时的超时时长,超时时,非核心线程会被回收。
unit:keepAliveTime的参数的时间单位,常用TimeUnit.SECONDS(秒),TimeUnit.MILLISECONDS(毫秒)。
workQueue:该线程池的任务队列,通过execute方法提交的Runnable对象会存储在这个队列中
threadFactory:线程工厂,为线程提供创建新线程的功能。
handler:不常用,用于线程池无法执行新任务时通过handler的rejectedExecution方法通知调用者。
下面以AsyncTask举例说明线程池的用法://获取Java虚拟机支持的并发数,一般是机器的核数 private static final int CPU_COUNT = Runtime.getRuntime().availableProcessors(); //设置线程池核心线程数 private static final int CORE_POOL_SIZE = CPU_COUNT + 1; //设置线程池容量 private static final int MAXIMUM_POOL_SIZE = CPU_COUNT*2 + 1; //设置线程超时时长1000ms private static final int KEEP_ALIVE_TIME = 1000; //创建一个容量为128的任务队列 private static final BlockingQueue<Runnable> sPoolWorkQueue = new LinkedBlockingDeque<Runnable>(128); private static final ThreadFactory sThreadFactory = new ThreadFactory() { private final AtomicInteger mCount = new AtomicInteger(1); @Override public Thread newThread(@NonNull Runnable r) { return new Thread(r,"AsyncTask #" + mCount.getAndIncrement()); } };ThreadPoolExecutor poolExecutor = new ThreadPoolExecutor(CORE_POOL_SIZE ,MAXIMUM_POOL_SIZE ,KEEP_ALIVE_TIME , TimeUnit.MILLISECONDS ,sPoolWorkQueue ,sThreadFactory);poolExecutor.execute(new Runnable() { @Override public void run() { try { Thread.sleep(2000); final String name = Thread.currentThread().getName(); Log.i(TAG, "run: " + name); } catch (InterruptedException e) { e.printStackTrace(); } } });简单用法就写到这了,后面看看写一写更深入的用法吧。