服务(Service)与活动(Activity)、广播接收器(Broadcast Receiver)、内容提供器(Content Provider)构成了Android系统的四大组件。活动和服务都是可以执行的程序,活动是android应用程序的门面,活动中都会设置布局界面,可以很好的与用户互动,而服务则没有用户界面,也绝不会到前台去,它在后台默默运行,一些耗时且不用跟用户交互的的程序往往选择服务。(比如计时Toast一段提示信息、需要耗时的下载任务,申请网页)
伟大的服务正如其名字一般,默默无闻在后台运行工作,把一切出风头的机会让给他的小弟活动,真真让人感动。正如一出华丽的舞台剧,活动如同舞台上光鲜亮丽的演员,而服务则是幕后的工作人员,他们的工作不被观众看到,但一出舞台剧的成功却不能够缺少后台工作者!
服务不依赖于用户界面,移至后台或开启另一程序,服务仍然可以运行。但是服务依赖于创建服务的应用程序进程,当应用程序被杀死,服务也会停止运行并销毁!需要注意自从Android 5.0开始,要求必须使用显式Intent启动Service组件。而在AndroidManfiest.xml文件中注册服务时,可为<service.../>元素配置<intent-filter/>子元素,用于说明该Service可以被哪些特定Intent启动
生命周期:
关于服务的生命周期问题可见我原创另一篇博客http://blog.csdn.net/whatever9527/article/details/53331838,通过startService()启动Service与通过bindService()方法启动Service的生命周期略有不同。这里补充一条:当Service通过startService启动并且绑定活动后再解绑,且Service子类中重写了onUnbind()方法时返回true,则再试图绑定时会调用onRebind()方法,而不是onBind()方法。
前台服务:
通过重写onCreate()方法,将服务变身为前台服务。极其类似于通知(Notification)创建用法。
服务用法总结如下:
当访问者不需要与Service通信时,通过startService()方法启动服务,在onStartCommand()方法中放入希望服务一启动就执行的逻辑,返回一个int整型,start_sticky、start_no_sticky、START_REDELIVER_INTENT、START_STICKY_COMPATIBILITY。可以重写onCreate()方法在其中开启线程,只要没有被自己或调用者停止,会一直运行。
当访问者需要与Service通信,通过onBind()方法来启动Service,一、需要在Service子类中定义一个内部类继承于Binder,在这个Binder的子类中定义我们需要和访问者通信所用到的方法,重写Service子类中的onBind()方法,返回一个刚才定义的一个Binder的子类对象;二、在访问者(如MainActivity)中定义内部类ServiceConnection并且重写它的onServiceConnected()方法和onServiceDistonnected()方法,前者中一般给出提示“服务连接成功”并且通过向下转型实例化出所定义的Binder的子类对象,之后就可以利用此对象实现服务与访问者之间的通信了!
傻瓜式服务(IntentService)
需要注意的是使用普通服务,是需要自己手动创建并开启线程的,比如在onCreate()方法或onStartCommand()方法中启动新线程处理任务,而Android中提供了一个更为方便的工具,IntentService,它会自动创建work线程处理所有的Intent请求,并且在任务结束后会自动停止服务,根本不需要我们自己处理多线程问题,可以说是方便至极的傻瓜式服务!
IntentService不需要我们自己重写onStartCommand()方法或onBind()方法,只需首先提供一个无参构造方法,在其内部调用父类有参构造方法,然后重写onHandleIntent()方法,在其中写具体耗时逻辑,这个方法内逻辑已经是在子线程中运行的了,不会出现ANR(application not responding)。