Android多進程運行機制及IPC

作者:躬行之

今天總結下 Android 多進程運行機制以及 IPC 介紹,內容如下:

  1. Android中的進程
  2. Android IPC介紹
  3. 開啓多進程模式
  4. Android多進程運行機制

Android中的進程

首先進程可以理解爲獨立運行的程序,當某個程序啓動時,系統將會爲該程序創建一個進程,併爲其分配所需的系統資源,同時將該進程添加到進程就緒隊列中,進程調動程序負責運行哪一個進程。

Android 中的應用程序可以爲一個進程,也可以配置成多進程,每個進程都在自己獨立的空間中運行,Android 爲每個進程分配一個虛擬機,不同的虛擬機在內存分配上有不同的地址空間,不同的進程自然涉及到進程間通信。

Android 中的進程如下:

  • 前臺進程:可與用戶直接交互或與前臺綁定的Service所在的進程;
  • 可見進程:用戶可見但是不可點擊;
  • 服務進程:後臺執行的 Service 所在的進程;
  • 後臺進程:相對於前臺進程而言的進程;
  • 空進程:理解爲一種緩存意義上的進程,系統隨時可以選擇回收空進程。

其優先級爲前臺進程 > 可見進程 > 服務進程 > 後臺進程 > 空進程。

Android IPC介紹

IPC(Inter-Process Communication) 指的是進程間通信或跨進程通信,任何一個操作系統都需要相應的 IPC 機制來完成進程間通信,如 Windows 上可以通過剪切板、管道等來完成進程間通信,Linux 上可以通過信道、共享內存、信號量來進行進程間通信Android 雖然基於 Linux,但是爲了適應移動端的特點,專門提供了一種進程間通信方式 Binder,所以說到 Android 中的 IPC 機制,一般指的就是 Android 中的 Binder 機制。

IPC使用場景:

  1. 某些應用自身需要採用多進程模式,如在 Android 中對一個應用獲取的最大內存做了限制,爲了使自己的應用獲取更多內存空間而將一些模塊放在獨立進程中,此時模塊之間的交互就需要進程間通信來完成;
  2. 應用本身需要跨進程與其他應用交互,無論是使用 ContentProvider 還是 AIDL 都屬於 IPC 的範疇,如在 Android 機頂盒 IPTV 中間件中就有大量使用。

注意:Android 對應用內存的限制不同廠商不同,默認分配的初始內存是 16M,具體配置在 system/build.prop 文件中。

開啓多進程模式

Android 中開啓多進程是在四大組件中配置 android:process 屬性來開啓多進程,配置時可以配置成私有進程和全局進程,如下:

<!--私有進程-->
<!--com.manu.progress:remote-->
<activity 
    android:name="com.manu.process.SampleActivity"
    android:process=":remote"/>
<!--全局進程-->
<!--com.manu.remote-->
<activity 
    android:name="com.manu.process.SampleActivity"
    android:process="com.manu.remote"/>

如果配置成私有進程,則其他應用的組件不可與其跑在同一個進程中,如果配置全局進程,則可以將兩個應用設置成相同的 ShareUID 將兩個應用的組件運行在同一個進程中,除此之外這兩個應用的簽名也得相同,這樣將可將兩個應用的組件運行在同一進程中,且可以共享私有數據如 data 目錄等。

那麼怎麼將兩個應用的組件配置在同一進程呢?

  1. 兩個應用設置相同的 ShareUID
  2. 兩個應用的兩個組件的進程設置成進程名相同的全局進程
  3. 兩個應用簽名相同

測試過程中發現,如果一個進程已經啓動了,在啓動一個配置同一進程的組件時,第二個應用程序會異常退出,這一點還需閱讀源碼進一步瞭解原因.

  • 怎麼將兩個應用的組件配置在同一進程呢?

Android多進程運行機制

Android 爲每個進程分配一個獨立的虛擬機,不同的虛擬機在內存分配上有不同的地址空間,這就導致在不同的虛擬機中訪問同一個類的對象會產生多份副本,也就是說在兩個進程中存在着同一個類的兩個副本,這兩個類互不干擾,修改一個不會影響另一個,這就導致了一個問題,即運行在不同進程中的四大組件,只要它們之間通過內存來共享數據,都會共享失敗,多進程造成的問題如下:

  1. 靜態成員和單例模式完全失效

多進程中在着一個類的多個副本,修改互不影響,自然無法生效;

  1. 線程同步機制完全失效

線程同步機制鎖住的不是一個對象,自然無法生效;

  1. SharePreference的可靠性下降

SharePreference 雖然可以設置 MODE_MULTI_PROCESS 支持多進程,但是並不推薦使用,因爲在某些版本上不生效,在 API 23 之後已被廢棄,所以使用 MODE_MULTI_PROCESS 支持 SharePreference 多進程是不靠譜的,解決方案是使用 ContentProvider 作爲中間層來使的 SharePreferences 來支持多進程。

具體就是其他進程通過 ContentProvider 來訪問另一個進程,而數據是存儲在 SharePreference 中的,可通過 Contentprovider 實現增刪查改來對數據進行操作。

  1. Application多次創建

當一個組件運行到一個新的進程時,創建進程的過程實際上就是一個應用啓動的過程,自然會使得 Application 多次創建,可以這樣理解爲運行在同一進程中的組件是屬於同一個虛擬機和同一個 Application 的,不同進程中的組件屬於多個虛擬機和 Application。

Application 的 onCreate 方法一般用來初始化操作,如果多次調用 Application 的 onCreate 方法,爲避免出錯,可根據進程名判斷再進行相關初始化。

最後

如果還想了解更多Android 相關的更多知識點,可以點進我的GitHub項目中:https://github.com/733gh/GH-Android-Review-master自行查看,裏面記錄了許多的Android 知識點。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章