Android創(chuàng)建多進(jìn)程

為何要使用多進(jìn)程

1.分散內(nèi)存的占用
我們知道Android系統(tǒng)對(duì)每個(gè)應(yīng)用進(jìn)程的內(nèi)存占用是有限制的,而且占用內(nèi)存越大的進(jìn)程,通常被系統(tǒng)殺死的可能性越大。讓一個(gè)組件運(yùn)行在單獨(dú)的進(jìn)程中,可以減少主進(jìn)程所占用的內(nèi)存,避免OOM問(wèn)題,降低被系統(tǒng)殺死的概率。
2.子進(jìn)程和主進(jìn)程崩潰互不影響
我們?cè)谧舆M(jìn)程長(zhǎng)時(shí)間運(yùn)行,比如音樂,推送等,如果子進(jìn)程崩潰了,不會(huì)影響主進(jìn)程。反之主進(jìn)程崩潰了,不會(huì)影響子進(jìn)程的功能使用。
3.實(shí)現(xiàn)守護(hù)進(jìn)程
如果主線程中的服務(wù)要從開機(jī)起持續(xù)運(yùn)行,若由于內(nèi)存等原因被系統(tǒng)kill掉,守護(hù)進(jìn)程可以重新啟動(dòng)主線程的服務(wù)。
通過(guò)JNI利用C/C++,調(diào)用fork()方法來(lái)生成子進(jìn)程,一般開發(fā)者會(huì)利用這種方法來(lái)做一些daemon(守護(hù)進(jìn)程)進(jìn)程,來(lái)實(shí)現(xiàn)防殺?;畹刃Ч?/p>

使用多進(jìn)程:

在開發(fā)中,我們通常會(huì)使用修改清單文件的android:process來(lái)達(dá)到多進(jìn)程的目的。activity、service、receiver 和 provider均支持android:process屬性,此屬性可以指定該組件應(yīng)在哪個(gè)進(jìn)程運(yùn)行。如果android:process的value值以冒號(hào)開頭的話,那么該進(jìn)程就是私有進(jìn)程,如果是以其他字符開頭,那么就是公有進(jìn)程,擁有相同 ShareUID 的不同應(yīng)用可以跑在同一進(jìn)程里。

私有進(jìn)程和公有進(jìn)程

私有進(jìn)程:
android:process=":remote",以冒號(hào)開頭,冒號(hào)后面的字符串原則上是可以隨意指定的,種設(shè)置形式表示該進(jìn)程為當(dāng)前應(yīng)用的私有進(jìn)程,其他應(yīng)用的組件不可以和它跑在同一個(gè)進(jìn)程中。

公有進(jìn)程:
進(jìn)程名稱不以“:”開頭、android:process值一定要有個(gè)點(diǎn)號(hào)的進(jìn)程都可以叫全局進(jìn)程,如android:process="com.secondProcess",以小寫字母開頭,表示運(yùn)行在一個(gè)以這個(gè)名字命名的全局進(jìn)程中,其他應(yīng)用通過(guò)設(shè)置相同的ShareUID可以和它跑在同一個(gè)進(jìn)程。

示例:

創(chuàng)建Application:

class MyApplication : Application() {

    override fun onCreate() {
        super.onCreate()

        var pid = android.os.Process.myPid()
        Log.d("TAG", "app pid = $pid")
    }
}

創(chuàng)建一個(gè)service:

class ProcessService : Service() {

    override fun onCreate() {
        super.onCreate()

        Log.d("TAG", "ProcessService onCreate")
    }

    override fun onBind(intent: Intent?): IBinder? {
        return null
    }
}

注冊(cè)ProcessService并聲明為一個(gè)獨(dú)立進(jìn)程

        <service android:name=".ProcessService"
            android:process="com.processService"/>

在MainActivity啟動(dòng)ProcessService進(jìn)程

class MainActivity : AppCompatActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        Log.d("TAG", "MainActivity onCreate")

        startService(Intent(this, ProcessService::class.java))
    }
}

執(zhí)行結(jié)果:


在不同的進(jìn)程中各自執(zhí)行了MainActivity和ProcessService的onCreate方法,并且執(zhí)行了2次Application的onCreate方法,執(zhí)行在不同的進(jìn)程中。

指定啟動(dòng)了新進(jìn)程,系統(tǒng)也會(huì)新建一個(gè)獨(dú)立的虛擬機(jī),自然需要重新初始化一遍Application。而我們會(huì)在Application的onCreate方法中做一些全局的初始化操作,它被初始化多次是完全沒有必要的。就需要解決Application重復(fù)初始化的問(wèn)題。

解決方案:

判斷是否為主進(jìn)程,只有主進(jìn)程的時(shí)候才執(zhí)行下面的操作,而且主進(jìn)程的pid為項(xiàng)目的包名,以此為依據(jù)判斷是否為主進(jìn)程。

MyApplication初始化加入進(jìn)程判斷:

class MyApplication : Application() {

    override fun onCreate() {
        super.onCreate()

        //多個(gè)Application創(chuàng)建的問(wèn)題:
        //避免重復(fù)初始化

        var processName = getProcessName()
        if (!TextUtils.isEmpty(processName) && processName.equals(packageName)) {

            //執(zhí)行初始化
            var pid = android.os.Process.myPid()
            Log.d("TAG", "app pid = $pid")
        }
    }
}
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • 一. 什么是多進(jìn)程? 多進(jìn)程就是多個(gè)進(jìn)程的意思,那么什么是進(jìn)程呢? 當(dāng)一個(gè)應(yīng)用在開始運(yùn)行時(shí),系統(tǒng)會(huì)為它創(chuàng)建一個(gè)進(jìn)程...
    醬拌飯閱讀 951評(píng)論 0 5
  • 進(jìn)程介紹 先強(qiáng)化兩個(gè)進(jìn)程相關(guān)的概念 進(jìn)程:進(jìn)程是一個(gè)具有一定獨(dú)立功能的程序關(guān)于某個(gè)數(shù)據(jù)集合的一次運(yùn)行活動(dòng),它是操作...
    a程序之路閱讀 4,342評(píng)論 0 3
  • 今天,了解到Android多進(jìn)程不僅僅是針對(duì)于AIDL,而像Application,Acitvity,Servic...
    星空下奔跑閱讀 499評(píng)論 0 0
  • 前言 其實(shí)很久之前就又知道多進(jìn)程這種方式,因?yàn)樵谖依斫庵蠴OM的最終解決方案就是使用此種方式,再加上之前就了解到插...
    清明捉鬼閱讀 347評(píng)論 0 1
  • 正常情況下,一個(gè)apk啟動(dòng)后只會(huì)運(yùn)行在一個(gè)進(jìn)程中,其進(jìn)程名為AndroidManifest.xml文件中指定的應(yīng)用...
    PeytonWu閱讀 4,730評(píng)論 0 2

友情鏈接更多精彩內(nèi)容