企业宣传,产品推广,广告招商,广告投放联系seowdb

Android多线程的四种形式

当咱们启动一个App的时刻,Android系统会启动一个Linux Process,该Process蕴含一个Thread,称为UI Thread或MainThread。通常一个运行的一切组件都运转在这一个Process中,当然,你可以经过修正四大组件在Manifest.xml中的代码块(<activity><service><provider><receiver>)中的android:process属性指定其运转在不同的process中。当一个组件在启动的时刻,假设该process曾经存在了,那么该组件就间接经过这个process被启动起来,并且运转在这个process的UIThread中。

UI Thread中运转着许多关键的逻辑,如系统事情解决,用户输入事情解决,UI绘制,Service,Alarm等,如下图:

UI Thread蕴含的逻辑

而咱们编写的代码则是交叉在这些逻辑两边,比如对用户触摸事情的检测和照应,对用户输入的解决,自定义View的绘制等。假设咱们拔出的代码比价耗时,如网络恳求或数据库读取,就会阻塞UI线程其余逻辑的口头,从而造成界面卡顿。假设卡登期间超越5秒,系统就会报ANR失误。所以,假设要口头耗时的操作,咱们须要另起线程口头。

在新线程口头完耗时的逻辑后,往往须要将结果反应给界面,启动UI降级。Android的UItoolkit不是线程安保的,不能在非UI线程启动UI的降级,一切对界面的降级肯定在UI线程启动。

Android提供了四种罕用的操作多线程的形式,区分是:

1. Handler+Thread

2. AsyncTask

3. ThreadPoolExecutor

4. IntentService

上方散布对四种形式启动引见。

Handler+Thread

Android主线程蕴含一个信息队列(MessageQueue),该信息队列外面可以存入一系列的Message或Runnable对象。经过一个Handler你可以往这个信息队列发送Message或许Runnable对象,并且解决这些对象。每次你新创立一个Handle对象,它会绑定于创立它的线程(也就是UI线程)以及该线程的信息队列,从这时起,这个handler就会开局把Message或Runnable对象传递到信息队列中,并在它们出队列的时刻口头它们。

Handler Thread原理图

Handler可以把一个Message对象或许Runnable对象压入到信息队列中,进而在UI线程中失掉Message或许口头Runnable对象,Handler把压入信息队列有两类形式,Post和sendMessage:

Post形式:

Post准许把一个Runnable对象入队到信息队列中。它的方法有:

post(Runnable)/postAtTime(Runnable,long)/postDelayed(Runnable,long)

关于Handler的Post形式来说,它会传递一个Runnable对象到信息队列中,在这个Runnable对象中,重写run()方法。普通在这个run()方法中写入须要在UI线程上的操作。

handler post用法

sendMessage:

sendMessage准许把一个蕴含信息数据的Message对象压入到信息队列中。它的方法有:sendEmptyMessage(int)/sendMessage(Message)/sendMessageAtTime(Message,long)/sendMessageDelayed(Message,long)

Handler假设经常使用sendMessage的形式把信息入队到信息队列中,须要传递一个Message对象,而在Handler中,须要重写handleMessage()方法,用于失掉上班线程传递上来的信息,此方法运转在UI线程上。Message是一个final类,所以无法被承袭。

handler定义

handler sendMessage用法

优缺陷

1. Handler用法繁难明了,可以将多个异步义务降级UI的代码放在一同,明晰明了

2. 解决单个异步义务代码略显多

实用范畴

1.多个异步义务的降级UI

AsyncTask是android提供的轻量级的异步类,可以间接承袭AsyncTask,在类中成功异步操作,并提供接口反应异步口头的水平(可以经过接口成功UI进展降级),***反应口头的结果给UI主线程。

AsyncTask经过一个阻塞队列BlockingQuery<Runnable>存储待口头的义务,应用静态线程池THREAD_POOL_EXECUTOR提供肯定数量的线程,自动128个。在Android3.0以前,自动采取的是并行义务口头器,3.0改成了自动驳回串行义务口头器,经过静态串行义务口头器SERIAL_EXECUTOR控制义务串行口头,循环取出义务交给THREAD_POOL_EXECUTOR中的线程口头,口头完一个,再口头下一个。

用法举例:

//前面尖括号内区分是参数(例子里是线程劳动期间),进展(publishProgress用到),前往值类型//第二个口头方法,onPreExecute()口头完后口头//这个函数在doInBackground调用publishProgress时触发,虽然调用时只要一个参数//然而这里取到的是一个数组,所以要用progesss[0]来取值//doInBackground前往时触发,换句话说,就是doInBackground口头完后触发//这里的result就是上方doInBackground口头后的前往值,所以这里是

优缺陷

1. 解决单个异步义务繁难,可以失掉到异步义务的进展

2. 可以经过cancel方法敞开还没口头完的AsyncTask

3. 解决多个异步义务代码显得较多

实用范畴

1.单个异步义务的解决

ThreadPoolExecutor

ThreadPoolExecutor提供了一组线程池,可以治理多个线程并行口头。这样一方面缩小了每个并行义务独自建设线程的开支,另一方面可以治理多个并发线程的公共资源,从而提高了多线程的效率。所以ThreadPoolExecutor比拟适宜一组义务的口头。Executors应用工厂形式对ThreadPoolExecutor启动了封装,经常使用起来愈加繁难。

ThreadPoolExecutor

Executors提供了四种创立ExecutorService的方法,他们的经常使用场景如下:

1. Executors.newCachedThreadPool()

创立一个定长的线程池,每提交一个义务就创立一个线程,直抵到达池的***长度,这时线程池会坚持长度不再变动

2. Executors.newFixedThreadPool()

创立一个可缓存的线程池,假设线程池的长度超越了解决的须要时,它可以灵敏的回收闲暇的线程,当须要参与时,

它可以灵敏的参与新的线程,而不会对池的长度作任何限度

3. Executors.newScheduledThreadPool()

创立一个定长的线程池,而且支持定时的以及周期性的义务口头,相似于Timer

4. Executors.newSingleThreadExecutor()

创立一个复线程化的executor,它只创立惟一的worker线程来口头义务

实用范畴

1. 批解决义务

IntentService

IntentService承袭自Service,是一个经过包装的轻量级的Service,用来接纳并解决经过Intent传递的异步恳求。客户端经过调用startService(Intent)启动一个IntentService,应用一个work线程依次解决顺序上来的恳求,解决成功后智能完结Service。

特点

1. 一个可以解决异步义务的繁难Service

原文链接:

© 版权声明
评论 抢沙发
加载中~
每日一言
不怕万人阻挡,只怕自己投降
Not afraid of people blocking, I'm afraid their surrender