服务
Service
是Android中实现程序后台运行的解决方案,它非常适合去执行那些不需要和用户交互而且还要求长期运行的任务
1.多线程编程
1.1 线程的基本用法
- 继承
Thread
类
class MyThread extends Thread{
@override
public void run(){
}
}
MyThread mThread = new MyThread();
mThread.start();
- 实现
Runnable
接口
class MyThread implements Runnable{
@override
public void run(){
}
}
MyThread mThread = new MyThread();
new Thread(mThread).start();
3.匿名类
new Runnable(new Runnable{
@override
public void run(){
}
}).start();
1.2 在子线程中更新UI
Android中的UI是线程不安全的,也就是说,如果想要更新程序里的UI元素,则必须在主线程中进行。但有时我们必须要在子线程里面执行一些耗时操作,对于这种情况,Android提供了一套异步消息处理机制,完美解决了问题。
异步消息处理机制基本的异步消息处理机制总共分为3个步骤:
- 定义Handler
private Handler handler = new Handler() {
public void handleMessage(Message msg){
switch(msg.what){
case UPDATE_TEXT:
//UI操作
}}};
- 实例化Message对象
Message msg = new Message();
msg.what = UPDATE_TEXT
- handler发送消息
handler.sendMessage(msg);
1.2.1 Handler机制详解
Message
- 线程之间传递的信息,可携带少量的信息
- 可以设置的字段有:
obj
,what
,arg1
,arg2
MessageQueue
- 消息队列,暂时存放消息
- 串行执行
- 每个线程只有1个
MessageQueue
Handler
- 发送消息和处理消息
-
Looper
MessageQueue
的管家,将MessageQueue
中的消息取出,放入Handler
的handleMessage()
中
1.2.2 AsyncTask
AsyncTask
是一个抽象类,需要继承使用
可以传入3个泛型参数
-
Params
在执行AsyncTask时需要传入的参数,可用于在后台任务中使用 -
Progress
后台执行r任务执行时进度单位 -
Result
任务执行完毕的结果类型
需要继承4个方法
-
onPreExecute()
执行一些界面上的初始化操作,比如显示一个进度条对话框等 -
doInBackground(Params)
处理所有的耗时任务,任务完成后可以用return将结果返回
注意:这个方法不能进行UI操作 -
onProgressUpdate(Progress)
在执行publishProgress(Progress)
后,onProgressUpdate(Progress)
就会被调用,可以来进行一些UI操作 onPostExecute(Result)
启动
new DownloadTask().execute();
2.服务的基本用法
2.1 定义一个服务
- 继承Service类
public class MyService extends Service {
public MyService(){}
@Override
public IBinder onBind(Intent intent){
}
}
}
- 实现方法
-
onCreate()
服务创建时调用 -
onStartCommand(Intent intent, int flags, int startId)
服务启动时调用 -
onDestroy()
服务销毁时调用
3.注册Service
<Service
android:name = ".MyService"
android:enabled="true"
android:exported="true">
</Service>
2.2 启动和停止服务
-
Intent
开始和启动
Intent startIntent = new Intent(MainActivity.this, MyService.class);
startService(startIntent); //Context类
// stopService(startIntent);
- 自己停止
stopself()
调用后能让服务停止下来
2.3 活动和服务进行通信
步骤:
1.在服务中创建内部类downloadBinder
继承至Binder
,主要实现一些方法
2.Service
类中的onBind
方法将downloadBinder
暴露给客户端
3.客户端MainActivity
中在onServiceConnected
中接受服务端的downloadBinder
并使用其中的方法
4.使用bindService(intent,connection,BIND_AUTO_CREATE)
开启服务
5.解绑服务使用unbindService(connection)
3.服务的生命周期
服务的生命周期3.1 服务的启动方式对比
如上述所说,服务的启动方式有两中,一种是startService
,一种是bindService
这两种启动服务的方式具体有什么不同?
第一种是通过
startservice
方式来启动,通过此方式来启动的service
会一直运行在后台,除非调用者主动停止服务或者是系统异常杀死。 此过程对应的生命周期是:onCreate()----onStartCommand()-----onStop()----onDestory()
- 只会创建一个
Service
实例,onCreate
只会执行一次,onStartCommand
在每次startService
的时候执行 - 适用于简单的服务启动
第二种是通过
bindService
方式来启动,通过此方式来启动的service
会和调用者的生命周期绑定,调用者被销毁的时候,service也会被销毁, 此过程对应的生命周期是:onCreate()----onBind()-----onUnbind()----onStop()----onDestory()
- 当我们使用同一个
context
和serviceconnection
去执行bindservice
时,onServiceConnected
方法只会被回调一次 - 直接
finish()
,不会调用unbindService方法,Service在Activity销毁后,自行解除绑定然后销毁。 - 适用于需要活动和Service数据交互的场景
4.IntentService
- Service运行在主线程,因此不能处理大量耗时的操作,于是可以尝试开启线程
- Service中开启线程和运行完后停止服务这两个操作经常容易忘记
因此,Android提供了IntentService。它需要实现onHandleIntent()
和onDestroy()
两个函数
网友评论