線程池android,線程池拒絕策略有哪些
Android線程池的使用
在Android中有主線程和子線程的區(qū)分。主線程又稱為UI線程,主要是處理一些和界面相關(guān)的事情,而子線程主要是用于處理一些耗時比較大的一些任務(wù),例如一些網(wǎng)絡(luò)操作,IO請求等。如果在主線程中處理這些耗時的任務(wù),則有可能會出現(xiàn)ANR現(xiàn)象(App直接卡死)。
線程池,從名字的表明含義上我們知道線程池就是包含線程的一個池子,它起到新建線程、管理線程、調(diào)度線程等作用。
既然Android中已經(jīng)有了線程的概念,那么為什么需要使用線程池呢?我們從兩個方面給出使用線程池的原因。
在Android中線程池就是ThreadPoolExecutor對象。我們先來看一下ThreadPoolExecutor的構(gòu)造函數(shù)。
我們分別說一下當(dāng)前的幾個參數(shù)的含義:
第一個參數(shù)corePoolSize為 核心線程數(shù) ,也就是說線程池中至少有這么多的線程,即使存在的這些線程沒有執(zhí)行任務(wù)。但是有一個例外就是,如果在線程池中設(shè)置了allowCoreThreadTimeOut為true,那么在 超時時間(keepAliveTime) 到達后核心線程也會被銷毀。
第二個參數(shù)maximumPoolSize為 線程池中的最大線程數(shù) 。當(dāng)活動線程數(shù)達到這個數(shù)后,后續(xù)添加的新任務(wù)會被阻塞。
第三個參數(shù)keepAliveTime為 線程的?;顣r間 ,就是說如果線程池中有多于核心線程數(shù)的線程,那么在線程沒有任務(wù)的那一刻起開始計時,如果超過了keepAliveTime,還沒有新的任務(wù)過來,則該線程就要被銷毀。同時如果設(shè)置了allowCoreThreadTimeOut為true,該時間也就是上面第一條所說的 超時時間 。
第四個參數(shù)unit為 第三個參數(shù)的計時單位 ,有毫秒、秒等。
第五個參數(shù)workQueue為 線程池中的任務(wù)隊列 ,該隊列持有由execute方法傳遞過來的Runnable對象(Runnable對象就是一個任務(wù))。這個任務(wù)隊列的類型是BlockQueue類型,也就是阻塞隊列,當(dāng)隊列的任務(wù)數(shù)為0時,取任務(wù)的操作會被阻塞;當(dāng)隊列的任務(wù)數(shù)滿了(活動線程達到了最大線程數(shù)),添加操作就會阻塞。
第六個參數(shù)threadFactory為 線程工廠 ,當(dāng)線程池需要創(chuàng)建一個新線程時,使用線程工廠來給線程池提供一個線程。
第七個參數(shù)handler為 拒絕策略 ,當(dāng)線程池使用有界隊列時(也就是第五個參數(shù)),如果隊列滿了,任務(wù)添加到線程池的時候的一個拒絕策略。
可以看到FixedThreadPool的構(gòu)建調(diào)用了ThreadPoolExecutor的構(gòu)造函數(shù)。從上面的調(diào)用中可以看出FixedThreadPool的幾個特點:
可以看到CacheThreadPool的構(gòu)建調(diào)用了ThreadPoolExecutor的構(gòu)造函數(shù)。從上面的調(diào)用中可以看出CacheThreadPool的幾個特點:
可以看到ScheduledThreadPoolExecutor的構(gòu)建調(diào)用了ThreadPoolExecutor的構(gòu)造函數(shù)。從上面的調(diào)用中可以看出ScheduledThreadPoolExecutor的幾個特點:
可以看到SingleThreadExecutor的構(gòu)建調(diào)用了ThreadPoolExecutor的構(gòu)造函數(shù)。從上面的調(diào)用中可以看出SingleThreadExecutor的幾個特點:
第十一章 Android的線程和線程池
執(zhí)行AsyncTask的execute方法,會執(zhí)行executeOnExecutor方法,該方法第一個參數(shù)是線程池,第二個是傳給AsyncTask的參數(shù)
在該方法里,首先會調(diào)用onPreExecute方法,然后將傳進來的參數(shù)賦值給mWorker.params,再調(diào)用第一個參數(shù)線程池的execute方法,傳入mFuture
如果是AsyncTask的默認線程池SerialExecutor,則只是用于排隊,使AsyncTask提交的任務(wù)一個一個的執(zhí)行。最終執(zhí)行是放在THREAD_POOL_EXECUTER線程池中執(zhí)行的
執(zhí)行mFuture的run方法,最終調(diào)用mWorker對象的call方法,在call方法里,會執(zhí)行doInBackground方法,返回一個Result對象,傳入postResult方法里
在postResult方法里,會利用sHandler即主線程的handler把Result發(fā)送到主線程進行處理,在handler的handMessage方法中,會調(diào)用onPostExecute方法,將結(jié)果發(fā)送到主線程
如果需要更新進度,可在doInBackground方法里調(diào)publishProgress方法,傳入進度信息,publishProgress方法里就會通過sHandler把進度信息傳到主線程
Android中的線程池
?線程池的好處
1、重用線程池中的線程,避免線程的創(chuàng)建與銷毀帶來的性能開銷
2、能有效控制線程池的最大并發(fā)數(shù),避免大量線程因搶占資源而導(dǎo)致的阻塞
3、能對線程進行簡單的管理,提供定時或者指定間隔時間、循環(huán)執(zhí)行等操作
線程池的概率來自于java的Executor接口,實現(xiàn)類是ThreadPoolExecutor, 它提供一系列的參數(shù)來配置線程池,以此構(gòu)建不同的線程池。Android的線程池分4類,都是通過Executors所提供的工廠方法來得到。
ThreadPoolExecutor有四個構(gòu)造函數(shù),下面這個是最常用的
public?ThreadPoolExecutor(int corePoolSize, int maximumPoolSize, long keepAliveTime, TimeUnit unit, BlockingQueueRunnnable workQueue, ThreadFactory threadFactory)
corePoolSize
線程池中的核心線程數(shù),默認情況下核心線程會在線程池中一直存活,即使他們處于閑置狀態(tài)。如果設(shè)置ThreadPoolExecutor 中的allowCoreThreadTimeOut = true, 核心線程在等待新任務(wù)到來時有超時機制,時間超過keepAliveTime所指定的時間后,核心線程會終止。
maximumPoolSize
最大線程數(shù)
keepAliveTime
非核心線程閑置的超時時間,超過這個時間,非核心線程會被回收。核心線程則要看allowCoreThreadTimeOut屬性的值。
unit
時間單位
workQueue
線程池中的工作隊列
threadFactory
線程工廠,為線程池提供創(chuàng)建新線程的功能。
舉個例子,我們常用的okhttp內(nèi)部也是使用了線程池,它的ThreadPoolExecutor主要是定義在Dispatcher類里面。 使用的是CachedThreadPool。
executorService = ThreadPoolExecutor(0, Int.MAX_VALUE, 60, TimeUnit.SECONDS, SynchronousQueue(), ThreadFactory("okhttp Dispatcher", false))
1、FixedThreadPool
通過Executors的newFixedThreadPool()創(chuàng)建,這是一個線程數(shù)量固定的線程池,里面所有的線程都是核心線程。
public static ExecutorService newFixedThreadPool(int nThreads){
return new ThreadPoolExecutor(nThreads, nThreads, 0, TimeUnit.MILLISECONDS, new LinkedBlockingQueueRunnable())
}
2、CachedThreadPool
通過Executors的newCacheThreadPool()創(chuàng)建,這是一個線程數(shù)量不定的線程池,里面所有的線程都是非核心線程。最大線程數(shù)是無限大,當(dāng)線程池中的線程都處于活動狀態(tài)時,新的task會創(chuàng)建新的線程來處理,否則就使用空閑的線程處理,所有的線程都是60s的超時時間,超時后會自動回收。
public static ExecutorService?newFixedThreadPool(){
return new ThreadPoolExecutor(0,?Integer.MAX_VALUE, 60L, TimeUnit.SECONDS, new SynchronousQueueRunnable())
}
3、ScheduledThreadPool
通過Executors的newScheduledThreadPool()創(chuàng)建, 核心線程固定,非核心線程無限大,當(dāng)非核心線程空閑時,會立即被回收。適合做定時任務(wù)或者固定周期的重復(fù)任務(wù)。
public static ExecutorService?newScheduledThreadPool(int corePoolSize){
return new ThreadPoolExecutor(corePoolSize,?Integer.MAX_VALUE, 0, TimeUnit.SECONDS, new DelayedWorkQueue())
}
4、SingleThreadExcecutor
通過Executors的newSingleThreadPool()創(chuàng)建,內(nèi)部只有一個核心線程。
public static ExecutorService?newFixedThreadPool(){
return new ThreadPoolExecutor(1,?1, 0, TimeUnit.MILLISECONDS, new LinkedBlockingQueueRunnable())
}
課外知識:LinkedBlockingQueue
LinkedBlockingQueue是由鏈表組成的阻塞隊列,內(nèi)部head 指向隊列第一個元素,last指向最后一個元素。入隊和出隊都會加鎖阻塞,都是使用了不同的鎖。
DelayedWorkQueue
延時隊列,隊內(nèi)元素必須是Delayed的實現(xiàn)類。對內(nèi)元素會按照Delayed時間進行排序,對內(nèi)元素只有在delayed時間過期了才能出隊。
入隊的時候不阻塞隊列,出隊的時候,如果隊列為空或者隊列里所有元素都等待時間都沒有到期,則該線程進入阻塞狀態(tài)。
Android中的線程和線程池
一、除了Thread外,扮演線程角色的還有:AsyncTask和IntentService,同時HandlerThread也扮演特殊的線程。
? ? ? IntentService:內(nèi)部采用HandlerThread來執(zhí)行,像一個后臺線程,同時是一個服務(wù),不容易被系統(tǒng)殺死。
二、HandlerThread的run方法是一個無限循環(huán)
三、IntentService中任務(wù)是排隊執(zhí)行的
四、AsyncTask?
1、Android1.6之前串行執(zhí)行任務(wù),1.6時候采用線程池里的并行,Android3.0開始又開始串行(為了避免并發(fā)錯誤),單任可以并行。
2、AsyncTask必須在UI線程調(diào)用(不過這個不是絕對的,和版本有關(guān)系,API 16之前,API 16到 22, API 22以后) 參考一
原因:內(nèi)部有靜態(tài)Handler,采用UI線程的Looper來處理消息,這就是為什么AsyncTask必須在UI線程調(diào)用,因為子線程默認沒有Looper無法創(chuàng)建下面的Handler,程序會直接Crash
3、AsyncTask中有兩個線程池和一個Handler,一個線程池用于任務(wù)排隊,一個線程池用于真正的執(zhí)行任務(wù),InternalHandler用于將
執(zhí)行環(huán)境從線程池切換到主線程
AsyncTask串行與并行
五、線程池
線程池中多余的線程是如何回收的
上一篇:android短信驗證碼,android免費的短信驗證碼api平臺
欄 目:其它綜合
下一篇:android連接網(wǎng)絡(luò),安卓網(wǎng)絡(luò)連接
本文標(biāo)題:線程池android,線程池拒絕策略有哪些
本文地址:http://www.jygsgssxh.com/a1/qitazonghe/17152.html
您可能感興趣的文章
- 04-02android傳智播客,傳智播客官網(wǎng)
- 04-02android發(fā)展前景,android前景分析
- 04-02android屏幕適配,android屏幕適配 大廠
- 04-02android說明,android csdn
- 04-02android素材,手機 素材
- 04-02android連接網(wǎng)絡(luò),安卓網(wǎng)絡(luò)連接
- 04-02android短信驗證碼,android免費的短信驗證碼api平臺
- 04-02android環(huán)境,android環(huán)境變量配置SDK
- 04-02騰訊手機管家forandroid,騰訊手機管家新版


閱讀排行
本欄相關(guān)
- 04-02android傳智播客,傳智播客官網(wǎng)
- 04-02android發(fā)展前景,android前景分析
- 04-02android屏幕適配,android屏幕適配 大廠
- 04-02android說明,android csdn
- 04-02android連接網(wǎng)絡(luò),安卓網(wǎng)絡(luò)連接
- 04-02android素材,手機 素材
- 04-02線程池android,線程池拒絕策略有哪些
- 04-02android環(huán)境,android環(huán)境變量配置SDK
- 04-02android短信驗證碼,android免費的短信驗
- 04-02騰訊手機管家forandroid,騰訊手機管家新
隨機閱讀
- 08-05dedecms(織夢)副欄目數(shù)量限制代碼修改
- 08-05DEDE織夢data目錄下的sessions文件夾有什
- 01-11Mac OSX 打開原生自帶讀寫NTFS功能(圖文
- 08-05織夢dedecms什么時候用欄目交叉功能?
- 01-11ajax實現(xiàn)頁面的局部加載
- 01-10C#中split用法實例總結(jié)
- 04-02jquery與jsp,用jquery
- 01-10SublimeText編譯C開發(fā)環(huán)境設(shè)置
- 01-10使用C語言求解撲克牌的順子及n個骰子
- 01-10delphi制作wav文件的方法


