(转载)Android开发——Android中常见的4种线程池(保证你能看懂并理解)

(转载)Android开发——Android中常见的4种线程池(保证你能看懂并理解)

大家好,又见面了,我是你们的朋友全栈君。

0.前言

转载请注明出处:http://blog.csdn.net/seu_calvin/article/details/52415337

使用线程池可以给我们带来很多好处,首先通过线程池中线程的重用,减少创建和销毁线程的性能开销。其次,能控制线程池中的并发数,否则会因为大量的线程争夺CPU资源造成阻塞。最后,线程池能够对线程进行管理,比如使用ScheduledThreadPool来设置延迟N秒后执行任务,并且每隔M秒循环执行一次。

下面会通过介绍线程池中的真正实现者——ThreadPoolExecutor来引出Android中的4类线程池的使用以及特性分析,会加上笔者自己的理解,和自认为比较恰当的比喻,帮助理解。

 

1.凡事得靠ThreadPoolExecutor(铺垫环节,懂的直接跳过)

Executor作为一个接口,它的具体实现就是ThreadPoolExecutor。

Android中的线程池都是直接或间接通过配置ThreadPoolExecutor来实现不同特性的线程池。

先介绍ThreadPoolExecutor的一个常用的构造方法。

 1 /* 
 2 *@ ThreadPoolExecutor构造参数介绍 
 3 *@author SEU_Calvin 
 4 * @date 2016/09/03 
 5 */  
 6 public ThreadPoolExecutor(  
 7 //核心线程数,除非allowCoreThreadTimeOut被设置为true,否则它闲着也不会死  
 8 int corePoolSize,   
 9 //最大线程数,活动线程数量超过它,后续任务就会排队                     
10 int maximumPoolSize,   
11 //超时时长,作用于非核心线程(allowCoreThreadTimeOut被设置为true时也会同时作用于核心线程),闲置超时便被回收             
12 long keepAliveTime,                            
13 //枚举类型,设置keepAliveTime的单位,有TimeUnit.MILLISECONDS(ms)、TimeUnit. SECONDS(s)等  
14 TimeUnit unit,  
15 //缓冲任务队列,线程池的execute方法会将Runnable对象存储起来  
16 BlockingQueue<Runnable> workQueue,  
17 //线程工厂接口,只有一个new Thread(Runnable r)方法,可为线程池创建新线程  
18 ThreadFactory threadFactory)  

ThreadPoolExecutor的各个参数所代表的特性注释中已经写的很清楚了,那么ThreadPoolExecutor执行任务时的心路历程是什么样的呢?(以下用currentSize表示线程池中当前线程数量)

(1)当currentSize<corePoolSize时,没什么好说的,直接启动一个核心线程并执行任务。

(2)当currentSize>=corePoolSize、并且workQueue未满时,添加进来的任务会被安排到workQueue中等待执行。

(3)当workQueue已满,但是currentSize<maximumPoolSize时,会立即开启一个非核心线程来执行任务。

(4)当currentSize>=corePoolSize、workQueue已满、并且currentSize>maximumPoolSize时,调用handler默认抛出RejectExecutionExpection异常。

 

2. Android中的四类线程池

Android中最常见的四类具有不同特性的线程池分别为FixThreadPool、CachedThreadPool、ScheduleThreadPool以及SingleThreadExecutor。

 

2.1     FixThreadPool(一堆人排队上公厕)

 1 /* 
 2 *@FixThreadPool介绍 
 3 *@author SEU_Calvin 
 4 * @date 2016/09/03 
 5 */  
 6 public static ExecutorService newFixThreadPool(int nThreads){  
 7     return new ThreadPoolExecutor(nThreads, nThreads, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue<Runnable>());  
 8 }  
 9 //使用  
10 Executors.newFixThreadPool(5).execute(r);  

(1)从配置参数来看,FixThreadPool只有核心线程,并且数量固定的,也不会被回收,所有线程都活动时,因为队列没有限制大小,新任务会等待执行。

(2)【前方高能,笔者脑洞】FixThreadPool其实就像一堆人排队上公厕一样,可以无数多人排队,但是厕所位置就那么多,而且没人上时,厕所也不会被拆迁,哈哈o(∩_∩)o ,很形象吧。

(3)由于线程不会回收,FixThreadPool会更快地响应外界请求,这也很容易理解,就好像有人突然想上厕所,公厕不是现用现建的。

 

2.2     SingleThreadPool(公厕里只有一个坑位)

 1 /* 
 2 *@SingleThreadPool介绍 
 3 *@author SEU_Calvin 
 4 * @date 2016/09/03 
 5 */  
 6 public static ExecutorService newSingleThreadPool (int nThreads){  
 7     return new FinalizableDelegatedExecutorService ( new ThreadPoolExecutor (1, 1, 0, TimeUnit. MILLISECONDS, new LinkedBlockingQueue<Runnable>()) );  
 8 }  
 9 //使用  
10 Executors.newSingleThreadPool ().execute(r);  

(1)从配置参数可以看出,SingleThreadPool只有一个核心线程,确保所有任务都在同一线程中按顺序完成。因此不需要处理线程同步的问题。

(2)【前方高能,笔者脑洞】可以把SingleThreadPool简单的理解为FixThreadPool的参数被手动设置为1的情况,即Executors.newFixThreadPool(1).execute(r)。所以SingleThreadPool可以理解为公厕里只有一个坑位,先来先上。为什么只有一个坑位呢,因为这个公厕是收费的,收费的大爷上年纪了,只能管理一个坑位,多了就管不过来了(线程同步问题)。

 

2.3     CachedThreadPool(一堆人去一家很大的咖啡馆喝咖啡)

 1 /* 
 2 *@CachedThreadPool介绍 
 3 *@author SEU_Calvin 
 4 * @date 2016/09/03 
 5 */  
 6 public static ExecutorService newCachedThreadPool(int nThreads){  
 7     return new ThreadPoolExecutor(0, Integer.MAX_VALUE, 60L, TimeUnit. SECONDS, new SynchronousQueue<Runnable>());  
 8 }  
 9 //使用  
10 Executors.newCachedThreadPool().execute(r);  

(1)CachedThreadPool只有非核心线程,最大线程数非常大,所有线程都活动时,会为新任务创建新线程,否则利用空闲线程(60s空闲时间,过了就会被回收,所以线程池中有0个线程的可能)处理任务。

(2)任务队列SynchronousQueue相当于一个空集合,导致任何任务都会被立即执行。

(3)【前方高能,笔者脑洞】CachedThreadPool就像是一堆人去一个很大的咖啡馆喝咖啡,里面服务员也很多,随时去,随时都可以喝到咖啡。但是为了响应国家的“光盘行动”,一个人喝剩下的咖啡会被保留60秒,供新来的客人使用,哈哈哈哈哈,好恶心啊。如果你运气好,没有剩下的咖啡,你会得到一杯新咖啡。但是以前客人剩下的咖啡超过60秒,就变质了,会被服务员回收掉。

(4)比较适合执行大量的耗时较少的任务。喝咖啡人挺多的,喝的时间也不长。

 

 

2.4    ScheduledThreadPool(4个里面唯一一个有延迟执行和周期重复执行的线程池)

 1 /* 
 2 *@ScheduledThreadPool介绍 
 3 *@author SEU_Calvin 
 4 * @date 2016/09/03 
 5 */  
 6 public static ScheduledExecutorService newScheduledThreadPool(int corePoolSize){  
 7 return new ScheduledThreadPoolExecutor(corePoolSize);  
 8 }  
 9 public ScheduledThreadPoolExecutor(int corePoolSize){  
10 super(corePoolSize, Integer.MAX_VALUE, 0, NANOSECONDS, new DelayedQueue ());  
11 }  
12 //使用,延迟1秒执行,每隔2秒执行一次Runnable r  
13 Executors. newScheduledThreadPool (5).scheduleAtFixedRate(r, 1000, 2000, TimeUnit.MILLISECONDS);

(1)核心线程数固定,非核心线程(闲着没活干会被立即回收)数没有限制。

(2)从上面代码也可以看出,ScheduledThreadPool主要用于执行定时任务以及有固定周期的重复任务。

 

至此Android中最常见的四类不同特性的线程池内容总结完毕。

转载请注明出处:http://blog.csdn.net/seu_calvin/article/details/52415337

转载于:https://www.cnblogs.com/1925yiyi/p/9040605.html

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/107514.html原文链接:https://javaforall.net

(0)
全栈程序员-站长的头像全栈程序员-站长


相关推荐

  • make menuconfig makefile kconfig详解

    make menuconfig makefile kconfig详解前面有一片文章分析makemenuconfig执行过程:http://blog.csdn.net/xinyuan510214/article/details/50964808今天,将一下makemenuconfigmakefilekconfig等几个容易混淆的关键操作。===1、内核Makefile概述(linux2.6)Linux内核的Makefile分为5个部分

    2022年5月27日
    61
  • 微信小程序滑动导航栏(网页浮动窗口怎么设置)

    一、前言做复杂的小程序就与web页面的区别原来越小了,一些web页面的功能会被要求添加到微信小程序页面中。二、功能页面在滑动的时候顶部页面导航跟随滑动,当点击导航中的任意一项时返回页面顶部。三、实现wxml代码:&lt;viewclass=’container’&gt;&lt;viewclass=’navigation{{pageVariable.isFloat==true?"fl…

    2022年4月14日
    222
  • Php公众号40029,微信公众号网页授权产生 错误代码:40029 真正解决

    Php公众号40029,微信公众号网页授权产生 错误代码:40029 真正解决在做微信二次开发的时候,调用网站授权接口会遇到{‘errcode’:40029,‘errmsg’:‘invalidcode,hints:[req_id:0407ns44]’}这样的错误。这个问题网上有很多所谓的解决方法,某些也确实能解决,我在开发过程中也遇到相同问题,下面记录一下我的解决方法。网上很多文章说,微信服务器发起了2次“相同”的请求,第一次请求被其终止掉了,我验证了一下,确…

    2022年4月30日
    195
  • 核PCA投影平面公式推导

    样本方差推导样本方差公式$$S=\frac{1}{n1}\sum_{i=1}^n(x_i\mu_i)^2$$扩展开来得到$$S=\frac{1}{n1}[(X\frac{1}{n}

    2021年12月30日
    45
  • 看懂 Serverless,这一篇就够了

    看懂 Serverless,这一篇就够了文章目录1.无服务器(Serverless)计算是什么2.理解Serverless技术—FaaS和BaaS2.1Faas(FunctionasaService,函数即服务)2.2Baas(BackendasaService,后端即服务)3.无服务器(Serverless)计算如何工作?4.无服务器(Serverless)适用于哪些场景?4.1场景一:应用负载有显著的波…

    2022年6月19日
    39
  • 软件测试人员应该如何介绍自己测试过的项目工作_软件测试项目介绍

    软件测试人员应该如何介绍自己测试过的项目工作_软件测试项目介绍测试人员在找工作的过程中,通常有一个问题是很难绕开的。就是要如何向别人介绍自己之前做过的项目。下面我们就这个问题简单的做一些分析。要解决这个问题,大体上可以分为如下几个步骤:1、对项目进行基本介绍2、说明自己负责测试的模块3、针对部分模块展开进行说明一.对项目进行基本介绍以下就以一个简单的项目进行介绍说明:最近测试的Tpshop项目是一个B/S架构的Web项…

    2022年10月20日
    0

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号