1. 程式人生 > >Android中Service(服務)詳解

Android中Service(服務)詳解

Service是Android中四大元件之一,在Android開發中起到非常重要的作用,先來看一下官方對Service的定義:

 is an application component that can perform long-running operations in the background and does not provide a user interface. Another application component can start a service and it will continue to run in the background even if the user switches to another application. Additionally, a component can bind to a service to interact with it and even perform interprocess communication (IPC). For example, a service might handle network transactions, play music, perform file I/O, or interact with a content provider, all from the background.


翻譯過來就是:Service(服務)是一個沒有使用者介面的在後臺執行執行耗時操作的應用元件。其他應用元件能夠啟動Service,並且當用戶切換到另外的應用場景,Service將持續在後臺執行。另外,一個元件能夠繫結到一個service與之互動(IPC機制),例如,一個service可能會處理網路操作,播放音樂,操作檔案I/O或者與內容提供者(content provider)互動,所有這些活動都是在後臺進行。

Service有兩種狀態,“啟動的”和“繫結”

Started A service is "started" when an application component (such as an activity) starts it by calling . Once started, a service can run in the background indefinitely, even if the component that started it is destroyed. Usually, a started service performs a single operation and does not return a result to the caller. For example, it might download or upload a file over the network. When the operation is done, the service should stop itself.
Bound

A service is "bound" when an application component binds to it by calling . A bound service offers a client-server interface that allows components to interact with the service, send requests, get results, and even do so across processes with interprocess communication (IPC). A bound service runs only as long as another application component is bound to it. Multiple components can bind to the service at once, but when all of them unbind, the service is destroyed.

通過startService()啟動的服務處於“啟動的”狀態,一旦啟動,service就在後臺執行,即使啟動它的應用元件已經被銷燬了。通常started狀態的service執行單任務並且不返回任何結果給啟動者。比如當下載或上傳一個檔案,當這項操作完成時,service應該停止它本身。

還有一種“繫結”狀態的service,通過呼叫bindService()來啟動,一個繫結的service提供一個允許元件與service互動的介面,可以傳送請求、獲取返回結果,還可以通過誇程序通訊來互動(IPC)。繫結的service只有當應用元件繫結後才能執行,多個元件可以繫結一個service,當呼叫unbind()方法時,這個service就會被銷燬了。

另外,在官方的說明文件中還有一個警告:

Caution: A service runs in the main thread of its hosting process—the service does not create its own thread and does not run in a separate process (unless you specify otherwise). This means that, if your service is going to do any CPU intensive work or blocking operations (such as MP3 playback or networking), you should create a new thread within the service to do that work. By using a separate thread, you will reduce the risk of Application Not Responding (ANR) errors and the application's main thread can remain dedicated to user interaction with your activities.

意思是service與activity一樣都存在與當前程序的主執行緒中,所以,一些阻塞UI的操作,比如耗時操作不能放在service裡進行,比如另外開啟一個執行緒來處理諸如網路請求的耗時操作。如果在service裡進行一些耗CPU和耗時操作,可能會引發ANR警告,這時應用會彈出是強制關閉還是等待的對話方塊。所以,對service的理解就是和activity平級的,只不過是看不見的,在後臺執行的一個元件,這也是為什麼和activity同被說為Android的基本元件。

Service生命週期中的一些方法:

                        

通過這個圖可以看到,兩種啟動service的方式以及他們的生命週期,bind service的不同之處在於當繫結的元件銷燬後,對應的service也就被kill了。service的宣告週期相比與activity的簡單了許多,只要好好理解兩種啟動service方式的異同就行。

service生命週期也涉及一些回撥方法,這些方法都不用呼叫父類方法,具體如下:

  1. <span style="font-family:Comic Sans MS;font-size:18px;">publicclass ExampleService extends Service {  
  2.     int mStartMode;       // indicates how to behave if the service is killed
  3.     IBinder mBinder;      // interface for clients that bind
  4.     boolean mAllowRebind; // indicates whether onRebind should be used
  5.     @Override
  6.     publicvoid onCreate() {  
  7.         // The service is being created
  8.     }  
  9.     @Override
  10.     publicint onStartCommand(Intent intent, int flags, int startId) {  
  11.         // The service is starting, due to a call to startService()
  12.         return mStartMode;  
  13.     }  
  14.     @Override
  15.     public IBinder onBind(Intent intent) {  
  16.         // A client is binding to the service with bindService()
  17.         return mBinder;  
  18.     }  
  19.     @Override
  20.     publicboolean onUnbind(Intent intent) {  
  21.         // All clients have unbound with unbindService()
  22.         return mAllowRebind;  
  23.     }  
  24.     @Override
  25.     publicvoid onRebind(Intent intent) {  
  26.         // A client is binding to the service with bindService(),
  27.         // after onUnbind() has already been called
  28.     }  
  29.     @Override
  30.     publicvoid onDestroy() {  
  31.         // The service is no longer used and is being destroyed
  32.     }  
  33. }</span>  

關於Service生命週期還有一張比較易懂的圖(來源於網路)


另外,這裡要說明Service的一個子類,IntentService,首先看下官方文件的說明:

This is a subclass of  that uses a worker thread to handle all start requests, one at a time. This is the best option if you don't require that your service handle multiple requests simultaneously. All you need to do is implement , which receives the intent for each start request so you can do the background work.

IntentService使用佇列的方式將請求的Intent加入佇列,然後開啟一個worker thread(執行緒)來處理佇列中的Intent,對於非同步的startService請求,IntentService會處理完成一個之後再處理第二個,每一個請求都會在一個單獨的worker thread中處理,不會阻塞應用程式的主執行緒,這裡就給我們提供了一個思路,如果有耗時的操作與其在Service裡面開啟新執行緒還不如使用IntentService來處理耗時操作。而在一般的繼承Service裡面如果要進行耗時操作就必須另開執行緒,但是使用IntentService就可以直接在裡面進行耗時操作,因為預設實現了一個worker thread。對於非同步的startService請求,IntentService會處理完成一個之後再處理第二個。

看下IntentService的具體實現:

  1. <span style="font-family:Comic Sans MS;font-size:18px;color:#222222;">publicclass HelloIntentService extends IntentService {  
  2.   /**  
  3.    * A constructor is required, and must call the super IntentService(String) 
  4.    * constructor with a name for the worker thread. 
  5.    */
  6.   public HelloIntentService() {  
  7.       super("HelloIntentService");  
  8.   }  
  9.   /** 
  10.    * The IntentService calls this method from the default worker thread with 
  11.    * the intent that started the service. When this method returns, IntentService 
  12.    * stops the service, as appropriate. 
  13.    */
  14.   @Override
  15.   protectedvoid onHandleIntent(Intent intent) {  
  16.       // Normally we would do some work here, like download a file.
  17.       // For our sample, we just sleep for 5 seconds.
  18.       long endTime = System.currentTimeMillis() + 5*1000;  
  19.       while (System.currentTimeMillis() < endTime) {  
  20.           synchronized (this) {  
  21.               try {  
  22.                   wait(endTime - System.currentTimeMillis());  
  23.               } catch (Exception e) {  
  24.               }  
  25.           }  
  26.       }  
  27.   }  
  28. }</span>  

關於停止Service,如果service是非繫結的,最終當任務完成時,為了節省系統資源,一定要停止service,可以通過stopSelf()來停止,也可以在其他元件中通過stopService()來停止,繫結的service可以通過onUnBind()來停止service。

關於Service還有很多知識,這裡就不再一一列舉,可以參考 http://developer.android.com/guide/components/services.html

相關推薦

AndroidService(服務)

Service是Android中四大元件之一,在Android開發中起到非常重要的作用,先來看一下官方對Service的定義: A  is an application component that can perform long-running operation

Android-Service 服務

一、Service的簡介 首先,相信很多Android開發者都知道Service是android 系統中的四大元件之一,它跟Activity的級別差不多,但是它只能後臺執行,並且可以和其他元件進行互動。service可以在很多場合的應用中使用,比如播放音樂的時候使用者啟動了其他Activ

Android service服務

為什麼要寫服務這篇文章 1.被老員工噴了 2.自己犯賤,撿西瓜丟芝麻,該打,555 服務是啥 服務是一個應用程式元件,可以在後臺執行長時間執行,不提供使用者介面。一個應用程式元件可以啟動一個服務,它將繼續在後臺執行,即使使用者切換到另一個應用程式。此外,一個元件可以繫結到一個

androidwifi原理(轉)

二:Wifi模組的初始化:: 在 SystemServer 啟動的時候,會生成一個ConnectivityService的例項, try { Log.i(TAG, "Starting Connectivity Service."); ServiceManager.addService(Con

AndroidJNI使用(4)---Java與C之間資料型別轉換

Jni中基本型別轉換對應的表格 Java型別 本地型別 說明 boolean jboolean 無符號,8位 byte jbyte

AndroidJNI使用(3)---Android StudioSO檔案生成

Android中JNI使用詳解(2)---Android Studio中SO檔案生成 上一篇寫到過在Android Studio中配置NDK環境地址:Android Studio中NDK環境配置 這篇文章講解在Android Studio中

AndroidJNI使用(2)---Android StudioNDK環境配置

Android Studio中的NDK環境配置 1、下載NKD 在Android Studio中選擇File----Settings----Appearance&Behavior---System Settings----Andr

AndroidJNI使用(1)---EclipseNDK配置So檔案生成

1、NDK下載和配置 NDK下載地址:http://www.androiddevtools.cn/ NDK下載完成後,選擇Eclipse上方Window選單Preferences - Android - NDK 在NDK&nb

Service 服務 及自定義服務模板

文章目錄 1、服務簡介 2、服務的生命週期 1) Service 的 啟動 停止 2)、服務的生命週期的方法 3、使用startService 啟動後服務

linuxapache服務4(企業級)ssl

ssl加密 yum install mod_ssl  -y      他是一個模組 yum install  crypto-utils  -y  加密 genkey www.westos.com

linuxapache服務3(企業級)cgi

對於cgi表單 mkdir -p /var/www/html/cgi semaneger fcontent -a -t httpd_sys_script_exec_t  '/var/www/html/cgi(/.*)?' restorecon -Rvvf  /va

linuxapache服務1(企業級)(http\cgi\php\ssl)

curl -I www.jd.com 檢視網站用的哪些服務 curl -I www.taobao.com firewall-config runtime 當前允許的狀態 permanent 永久允許的 html超文字標記語言 yum install  httpd  htt

androidwifi原理

                二:Wifi模組的初始化::在 SystemServer 啟動的時候,會生成一個ConnectivityService的例項,try {Log.i(TAG, "Starting Connectivity Service.");ServiceManager.addService(

AndroidSQLite應用

上次我向大家介紹了SQLite的基本資訊和使用過程,相信朋友們對SQLite已經有所瞭解了,那今天呢,我就和大家分享一下在Android中如何使用SQLite。 現在的主流移動裝置像Android、iPhone等都使用SQLite作為複雜資料的儲存引擎,在我們為移動裝置開發

Http——AndroidHttpURLConnection使用

認識Http協議 ndroid中傳送http網路請求是很常見的,要有GET請求和POST請求。一個完整的http請求需要經歷兩個過程:客戶端傳送請求到伺服器,然後伺服器將結果返回給客戶端,如下圖所示: 客戶端->伺服器  客戶端向伺服器傳送請求主要包含以下資

AndroidAsyncTask使用

在Android中我們可以通過Thread+Handler實現多執行緒通訊,一種經典的使用場景是:在新執行緒中進行耗時操作,當任務完成後通過Handler向主執行緒傳送Message,這樣主執行緒的Handler在收到該Message之後就可以進行更新UI的操作

[轉載]AndroidAndroidManifest.xml

一、關於AndroidManifest.xml AndroidManifest.xml 是每個android程式中必須的檔案。它位於整個專案的根目錄,描述了package中暴露的元件(activities, services, 等等),他們各自的實現類,各種能被處理的資料和

Android HttpURLConnection 使用

認識Http協議 Android中傳送http網路請求是很常見的,要有GET請求和POST請求。一個完整的http請求需要經歷兩個過程:客戶端傳送請求到伺服器,然後伺服器將結果返回給客戶端,如下圖所示: 客戶端->伺服器 客戶端向伺服器傳送請求主要包含以下

AndroidService使用

 本篇文章主要是講解一些關於Service的知識點。 Service的生命週期  Service有兩種啟動方式,startService與bindService。  首先來看startService,通過該方式啟動的Service與呼叫者沒有任何關聯,呼叫者也無法呼叫該Servi

Android的動畫系列【1】——逐幀動畫

逐幀動畫其實很簡單,下面我們來看一個例子:<?xml version="1.0" encoding="utf-8"?> <animation-list xmlns:andro