Android-Service生命周期
Service的基本概念,以及Service的生命周期:
一、Service的基本概念:
一个Service就是应用程序的组件,可以在后台长期跑,或者是为其他的应用提供功能上的支持。Service一般与Activity相对理解,它是没有Activity的界面的,Service也具有自己的独特生命周期,一个Service需要在AndroidManifest.xml中进行配置,
<application
android:allowBackup="true"
android:icon="@drawable/ic_launcher"
android:label="@string/app_name"
android:theme="@style/AppTheme" >
<activity
android:name="com.li.xiami.ServiceActivity1"
android:label="@string/app_name" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<service android:name=".StartActivity"></service>
</application>
注意:这个里面也可以增加android:process=".remote"来设置是远程调用,然后就是remote service
可以通过Context.startService()或者是Context.bindService()来启动Service;service是跑在宿主进程的主线程中,那么如果你的service需要做消耗CPU或者是阻塞的操作,那么应该重新开一个线程来处理这些耗时的操作。IntentService是继承自Service的,它会帮你重开一个线程来执行耗时操作。
注:Service既不是一个独立的进程,也不是一个线程,其实Service就是两个特性,也是跟生命周期结合起来的,一个是能够在后台一直跑,可以通过startService启动,一个是能够与其他应用进行交互,通过bindService建立连接,进行通信
Service具体的实现有两种,一个是localService,一个是通过AIDL来实现remoteService。
二、Service的生命周期:
先来一张经典的生命周期图示:

所涉及到的所有跟Service相关的函数包括:
onCreate()——Create只执行一次
onStartCommand()——可以多次执行
onDestory()——只执行一次
onBind()——绑定也只执行一次
onUnBind()——解绑也只执行一次
startService的生命周期:
onCreate()-onStartCommand()-onDestory():startService的时候会调onCreate(),但是只调一次,onStartCommand()可以被调用多次
StartService的程序实现:
package com.li.xiami; import android.app.Service;
import android.content.Intent;
import android.os.IBinder;
import android.util.Log; public class startService extends Service { private final String tag = "service"; @Override
public IBinder onBind(Intent intent) {
// TODO Auto-generated method stub
return null;
} @Override
public void onCreate() {
// TODO Auto-generated method stub
Log.v(tag, "onCreate()");
super.onCreate();
} @Override
public void onDestroy() {
// TODO Auto-generated method stub
Log.v(tag, "onDestory()");
super.onDestroy();
} @Override
public int onStartCommand(Intent intent, int flags, int startId) {
// TODO Auto-generated method stub
Log.v(tag, "onStartCommand()");
return super.onStartCommand(intent, flags, startId);
} }
package com.li.xiami; import android.os.Bundle;
import android.app.Activity;
import android.content.Intent;
import android.util.Log;
import android.view.Menu;
import android.view.View;
import android.widget.Button;
import android.widget.Toast; public class MainActivity extends Activity { private Button buttonstart;
private Button buttonstop;
private Button buttonsecondstart; private final String tag = "Activity"; Intent intent = new Intent(); @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main); buttonstart = (Button) findViewById(R.id.buttonstartservice);
buttonstop = (Button) findViewById(R.id.buttonstopservice);
buttonsecondstart = (Button) findViewById(R.id.buttonsencondstart); intent.setClass(MainActivity.this, startService.class); buttonstart.setOnClickListener(onClick);
buttonstop.setOnClickListener(onClick);
buttonsecondstart.setOnClickListener(onClick); } //这个匿名内部类的统一实现,要放在onCreate()的外面,这样这个先被初始化,然后onCreate()里面的button就能够找到这个对象
View.OnClickListener onClick = new View.OnClickListener() { @Override
public void onClick(View v) {
//switch里面写v.getId()。。。
switch(v.getId()){
case R.id.buttonstartservice:
//Toast.makeText().show()——之前只makeText了,也没有show()啊,笨蛋!!!
Toast.makeText(MainActivity.this, "startService", Toast.LENGTH_SHORT).show();
startService(intent);
Log.v(tag, "start service");
break;
case R.id.buttonstopservice:
Toast.makeText(MainActivity.this, "stopService", Toast.LENGTH_SHORT).show();
stopService(intent);
Log.v(tag, "stop service");
break; case R.id.buttonsencondstart:
Toast.makeText(getApplicationContext(), "secondStartService", Toast.LENGTH_SHORT).show();
startService(intent);
Log.v(tag, "second start service");
break; }
}
}; @Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
return true;
} }
AndroidManifest.xml中注册Service:
<service android:name=".startService"></service>
之后执行结果:

从startService的生命周期的运行log中就可以看到,Activity中执行startService()之后,Service执行回调函数onCreate()-onStartCommand(),之后再进行一次startService的话,只会执行onStartCommand(),Activity中执行stopService()的话,Service直接执行onDestory()。
Unbounded service:
bindService()的生命周期:
onCreate()-onBind()-onUnBind()-onDestory(),所有都是只执行一次,onBind()函数也是只执行一次
bindService的程序实现:(通过IBinder接口来实现,在Service中实现一个继承自Binder的类,然后在onBind()中返回一个Binder的对象,在Activity中通过得到这个Binder对象来进行通信)
package com.li.xiami; import android.app.Service;
import android.content.Intent;
import android.os.Binder;
import android.os.IBinder;
import android.util.Log; public class BindService extends Service { public final String tag = "service"; public class MyBinder extends Binder{
String state = "绑定绑定获取binder的数据";
String getState(){
return state;
}
} MyBinder mybinder = new MyBinder(); @Override
public IBinder onBind(Intent intent) {
// TODO Auto-generated method stub
Log.v(tag, "onBind()");
return mybinder;
} @Override
public void onCreate() {
// TODO Auto-generated method stub
Log.v(tag, "onCreate()");
super.onCreate();
} @Override
public void onDestroy() {
// TODO Auto-generated method stub
Log.v(tag, "onDestory()");
super.onDestroy();
} @Override
@Deprecated
public void onStart(Intent intent, int startId) {
// TODO Auto-generated method stub
Log.v(tag, "onStart()");
super.onStart(intent, startId);
} @Override
public int onStartCommand(Intent intent, int flags, int startId) {
// TODO Auto-generated method stub
Log.v(tag, "onStartCommand()");
return super.onStartCommand(intent, flags, startId);
} @Override
public boolean onUnbind(Intent intent) {
// TODO Auto-generated method stub
Log.v(tag, "onUnBind()");
return super.onUnbind(intent);
} }
package com.li.xiami; import com.li.xiami.BindService.MyBinder; import android.os.Bundle;
import android.os.IBinder;
import android.app.Activity;
import android.app.Service;
import android.content.ComponentName;
import android.content.Intent;
import android.content.ServiceConnection;
import android.util.Log;
import android.view.Menu;
import android.view.View;
import android.widget.Button;
import android.widget.Toast; public class MainActivity extends Activity { private Button buttonbind;
private Button buttongetstate;
private Button buttonunbind; Intent intent = new Intent();
BindService.MyBinder mybinder = null; private final String tag = "Activity"; boolean isBound = false; ServiceConnection conn = new ServiceConnection(){ @Override
public void onServiceConnected(ComponentName name, IBinder service) {
// TODO Auto-generated method stub
mybinder = (MyBinder) service;
} @Override
public void onServiceDisconnected(ComponentName name) {
// TODO Auto-generated method stub
mybinder = null;
} }; @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main); buttonbind = (Button) findViewById(R.id.buttonbind);
buttongetstate = (Button) findViewById(R.id.buttongetstate);
buttonunbind = (Button) findViewById(R.id.buttonunbind); intent.setClass(MainActivity.this, BindService.class); buttonbind.setOnClickListener(onClick);
buttongetstate.setOnClickListener(onClick);
buttonunbind.setOnClickListener(onClick); } View.OnClickListener onClick = new View.OnClickListener() { @Override
public void onClick(View v) {
// TODO Auto-generated method stub
switch(v.getId()){
case R.id.buttonbind:
Log.v(tag, "bindservice");
bindService(intent, conn, Service.BIND_AUTO_CREATE);
Toast.makeText(getApplicationContext(), "绑定服务", Toast.LENGTH_SHORT).show();
isBound = true;
break;
case R.id.buttongetstate:
Log.v(tag, "getstate");
if(isBound == true){
Toast.makeText(getApplicationContext(), "获取服务状态:"+mybinder.getState(), Toast.LENGTH_SHORT).show();
}
else{
Toast.makeText(getApplicationContext(), "还没绑定,请绑定", Toast.LENGTH_SHORT).show();
}
break;
case R.id.buttonunbind:
if(isBound == true){
Log.v(tag, "unbind");
Toast.makeText(getApplicationContext(), "解除绑定", Toast.LENGTH_SHORT).show();
unbindService(conn);
isBound = false;
}
else{
Toast.makeText(getApplicationContext(), "还没绑定,请绑定", Toast.LENGTH_SHORT).show();
}
break;
}
}
}; @Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
return true;
} }
AndroidManifest.xml中注册Service:
<service android:name=".BindService"></service>
之后执行结果:

从log中也可以看出,在Activity中多次执行bindService()也没有重复执行onBind()
Android-Service生命周期的更多相关文章
- Android Service生命周期及用法
Service概念及用途:Android中的服务,它与Activity不同,它是不能与用户交互的,不能自己启动的,运行在后台的程序,如果我们退出应用时,Service进程并没有结束,它仍然在后台运行, ...
- Android Service 生命周期
Service概念及用途: Android中的服务,它与Activity不同,它是不能与用户交互的,不能自己启动的,运行在后台的程序,如果我们退出应用时,Service进程并没有结束,它仍然在后台运行 ...
- Android Service 生命周期和使用注意项
一.基础知识 服务一般分为两种: 1:本地服务, Local Service 用于应用程序内部.在Service可以调用Context.startService()启动,调用Context.stopS ...
- 对于Android Service 生命周期进行全解析
应用程序组件有一个生命周期——一开始Android实例化他们响应意图,直到结束实例被销毁.在这期间,他们有时候处于激活状态,有时候处于非激 活状态:对于活动,对用户有时候可见,有时候不可见.组件生命周 ...
- Android Service生命周期 Service里面的onStartCommand()方法详解
在Demo上,Start一个Service之后,执行顺序:onCreate - > onStartCommand 然后关闭应用,会重新执行上面两步. 但是把代码拷贝到游戏工程发现,关闭游戏后,只 ...
- Service 生命周期
有了 Service 类我们如何启动他呢,有两种方法: • Context.startService() • Context.bindService() 1. 在同一个应用任何地方调用 start ...
- Android生命周期和Service生命周期
android生命周期 运行:oncreate → onstart → onresume暂停:onresume → onpause:再次运行:onresume停止:onpause → onstop → ...
- Android(java)学习笔记171:Service生命周期
1.Service的生命周期 Android中的Service(服务)与Activity不同,它是不能和用户交互,不能自己启动的,运行在后台的程序,如果我们退出应用的时候,Servic ...
- Android中startService的使用及Service生命周期
Android中有两种主要方式使用Service,通过调用Context的startService方法或调用Context的bindService方法.本文仅仅探讨纯startService的使用.不 ...
- Android(java)学习笔记114:Service生命周期
1.Service的生命周期 Android中的Service(服务)与Activity不同,它是不能和用户交互,不能自己启动的,运行在后台的程序,如果我们退出应用的时候,Servic ...
随机推荐
- 如何取Android设备日志
安装Android SDK 运行 adb 命令 adb devices 查看链接的设备 adb logcat 日志相关
- phpunit4.1的干净测试
一般而言,写测试时需要加载一些文件来进行自动加载 但在phpunit4.1中只要其中一个测试文件加载了,其他测试文件就不需要再加载
- python 类中staticmethod,classmethod,普通方法
1.staticmethod:静态方法和全局函数类似,但是通过类和对象调用. 2.classmethod:类方法和类相关的方法,第一个参数是class对象(不是实例对象).在python中class也 ...
- bootstrap模态框Esc键不关闭
项目开发时很多时候会需要用到弹出框,而且很多框架都有自己的弹出框,比较现在很流行的bootstrap就有模态框(model). 很多时候这东西用起来非常方便,可以为开发省去很多自己定义的时间!最近项目 ...
- 27个知名企业品牌VI视觉识别系统规范手册
Apple公司视觉设计规范 微软公司VI视觉系统 星巴克企业视觉规范手册 DELL品牌VI视觉手册 MTRADING品牌视觉规范 KFC视觉设计规范手册 麦当劳视觉规范 LEGO乐高玩具的品牌视觉规范 ...
- ant 构建时遇到 “非法字符: \65279”的解决办法
今天使用CI做版本构建时候碰到了这样一个问题,有个activity对应的java源码始终编译报错,错误发生在文件第一行. 出错内容是: *.java:1: 非法字符: \65279 [javac ...
- centos7优化mysql5.6配置
一.环境参数 [root@hn mysql]# grep 'physical id' /proc/cpuinfo |sort -u physical id : 0 physical id : 1 [r ...
- UNIX网络编程-基本API介绍(二)
参考链接:http://www.cnblogs.com/riky/archive/2006/11/24/570713.aspx 1.getsockname和getpeername getsocknam ...
- Runloop基础知识
*:first-child { margin-top: 0 !important; } body > *:last-child { margin-bottom: 0 !important; } ...
- IQ推理:红眼睛和蓝眼睛
题目: 有一个很古老的村子,这个村子的人分两种,红眼睛和蓝眼睛,这两种人并没有什么不同,小孩在没生出来之前,没人知道他是什么颜色的眼睛,这个村子中间有一个广 场,是村民们聚集的地方,现在这个村子只有 ...