Android线程池

优点

  1. 重用线池中的线程,避免因为线程的创建和销毁所带来的性能开销
  2. 能有效控制线程池的最大并发数,避免大量的线程之间因为互抢系统资源而导致的阻塞现象
  3. 能够对线程进行简单的管理,并提供定时执行以及指定间隔循环执行等功能

创建一个线程池需要的参数:

  1. corePoolSize 核心线程数大小。当提交一个任务时,如果当前线程数小于corePoolSize,就会创建一个线程。即使其他有可用的空闲线程。
  2. runnableTaskQueue(任务队列):用于保存等待执行的任务的阻塞队列。 可以选择以下几个阻塞队列
    (1) ArrayBlockingQueue:是一个基于数组结构的有界阻塞队列,此队列按 FIFO(先进先出)原则对元素进行排序。
    (2) LinkedBlockingQueue:一个基于链表结构的阻塞队列,此队列按FIFO (先进先出) 排序元素,吞吐量通常要高于ArrayBlockingQueue。静态工厂方法Executors.newFixedThreadPool()使用了这个队列。
    (3)SynchronousQueue:一个不存储元素的阻塞队列。每个插入操作必须等上一个元素被移除之后,否则插入操作一直处于阻塞状态,吞吐量通常要高于LinkedBlockingQueue,静态工厂方法Executors.newCachedThreadPool使用了这个队列。
    (4)PriorityBlockingQueue:一个具有优先级的无限阻塞队列。
  3. 不同的runnableTaskQueue对线程池运行逻辑有很大影响
  4. maximumPoolSize(线程池最大大小):线程池允许创建的最大线程数。如果队列满了,并且已创建的线程数小于最大线程数,则线程池会再创建新的线程执行任务。值得注意的是如果使用了无界的任务队列这个参数就没什么效果。

构造函数

public ThreadPoolExecutor(
            int corePoolSize,   //线程池的核心线程数
            int maximumPoolSize,//线程池容纳的最大线程数
            long keepAliveTime, //非核心线程闲置时的超时时长
            TimeUnit unit,     //用于指定keepAliveTime参数的时间单位
            BlockingQueue<Runnable> workQueue,   //线程池的任务队列
            ThreadFactory threadFactory          //线程工厂,为线程池提供创建新线程的功能
             )

ThreadPoolExector执行任务时大致规则如下:

  1. 如果线程池的线程数量为达到核心线程数量,那么会直接启动一个核心线程执行任务
  2. 如果线程池线程数量达到了或者超过了核心线程数量,那么任务会被插入到任务队列中排队等待执行
  3. 如果上一步骤无法将任务插入到任务队列中,这是因为任务队列已经满了,如果线程数量未达到线程池规定的最大值时,会立即启动一个非核心线程来执行任务.
  4. 如果上一步骤中的线程数量已经达到了线程池规定的最大数量,那么就拒绝执行此任务,会调用RejectedExecutionHandler的rejectedExecution方法来通知调用者.

AsyncTask对线程池的配置:

  • 核心线程数等于CPU核心数+1
  • 线程池的最大线程数为CPU核心数的2bei4+1
  • 核心线程无超时机制,非核心线程在闲置时的超时时间为1秒
  • 任务队列的容量为128

线程池的分类

1.FixedThreadPool

  • 线程数量固定的线程池,线程处于空闲状态的时候,他们不会被回收,除非线程池被关闭了
  • 只有核心线程数,并且不会被回收
  • 没有超时机制
  • 任务队列没有大小限制
  • 能够快速的对外界的请求作出响应

2.CacheThreadPool

  • 线程数量不固定的线程池,最大线程数为Integer.MAX_VALUE(很大的数)
  • 只有非核心线程
  • 有超时机制,超时60秒闲置线程就会被回收
  • 任务队列相当于一个空集合,任何任务都被立即执行
  • 适合执行大量的耗时较少的任务

3.ScheduledThreadPool

  • 核心线程数量固定的,非核心线程数没有限制的
  • 非核心线程数闲置的时候会被立即回收
  • 主要用于执行定时任务和具有固定周期的重复任务

4.SingleThreadPool

  • 只有一个核心线程数
  • 保证任务都在同一个线程中按顺序执行
  • 不需要处理线程同步的问题