Android學(xué)習(xí)筆記-四大組件-基礎(chǔ)知識(shí)1

????????該部分主要記錄ActivityService缎讼,BroadcastReceiver澎语,ContentProvider的基本知識(shí)和使用,關(guān)于高級(jí)部分后續(xù)將來不知道哪天的哪天可能或許會(huì)再寫一篇文章來記錄


Activity

????????對(duì)于Activity的地位不再過多敘述萍膛,是一個(gè)應(yīng)用向外界展示信息所必須的一個(gè)組件吭服。

生命周期

經(jīng)典的生命周期圖

activity_lifecycle.png

關(guān)于各個(gè)周期:
onCreate()
Activity被創(chuàng)建時(shí)首先調(diào)用。
onStart()
Activity界面出現(xiàn)時(shí)蝗罗。
onResume()
Activity被完全顯示艇棕,可以與用戶交互時(shí)。
onPause()
Activity失去焦點(diǎn)但仍對(duì)用戶可見串塑,如顯示了一個(gè)彈窗沼琉。
onStop()
Activity被其他Activity完全遮擋,對(duì)用戶不可見桩匪,如跳轉(zhuǎn)到新的Activity或者退出程序打瘪,直接鎖屏。
onDestory()
Activity被銷毀時(shí)調(diào)用傻昙。
onRestart()
Activity對(duì)象再次被啟動(dòng)時(shí)調(diào)用闺骚。

  • 正常啟動(dòng)生命周期
    onCreate()->onStart()->onResume()->activity runing->onPause()->onStop()->onDestory()
  • 被遮擋但可見不可操作又取消遮擋
    onPause()->activity stop->onResume()->activity runing
  • 不可見變?yōu)榭梢?/strong>
    onPause()->onStop()->activity stop->onRestart()->onStart()->onResume()->activity runing
    Activity示例代碼

啟動(dòng)模式

  • standard
    標(biāo)準(zhǔn)模式。
    Activity默認(rèn)的啟動(dòng)模式妆档,Activity每次啟動(dòng)都會(huì)在棧頂創(chuàng)建一個(gè)新的Activity實(shí)例僻爽。
    如果Activity已經(jīng)位于棧頂,則Activity啟動(dòng)時(shí)也將會(huì)重新創(chuàng)建新的實(shí)例贾惦。
  • singleTop
    棧頂復(fù)用模式胸梆。
    Activity啟動(dòng)時(shí)判斷其是否在棧頂,如果在棧頂則直接復(fù)用须板,并且回調(diào)onNewIntent()方法乳绕,不會(huì)再重新創(chuàng)建新的Activity實(shí)例。
    如果未處于棧頂則重新創(chuàng)建新的Activity實(shí)例逼纸。
  • singleTask
    棧內(nèi)復(fù)用模式洋措。
    1.Activity被首次創(chuàng)建時(shí)首先檢測(cè)AndroidManifest.xml中相應(yīng)<activity />節(jié)點(diǎn)下的android:taskAffinity="..."屬性是否存在,如果不存在則在啟動(dòng)該ActivityActivity所在的任務(wù)棧上新建該Activity杰刽,如果屬性值存在并與某一任務(wù)棧相同則在該任務(wù)棧中新建該Activity菠发,如果屬性名與已存在的任務(wù)棧都不相同則新建與屬性名相同的任務(wù)棧并新建該Activity王滤。
    2.Activity非首次創(chuàng)建啟動(dòng)時(shí)檢測(cè)活動(dòng)棧中是否已存在Activity實(shí)例,如果存在則直接復(fù)用并將其之上的所有Activity實(shí)例全部出棧滓鸠,并且回調(diào)onNewIntent()方法雁乡,使該Activity處于棧頂?shù)奈恢茫绻淮嬖趧t在棧頂創(chuàng)建新的Activity實(shí)例糜俗。
  • singleInstance
    單實(shí)例模式踱稍。
    該模式下Activity會(huì)啟動(dòng)一個(gè)新的任務(wù)棧來管理Activity實(shí)例,當(dāng)從其他任務(wù)棧中啟動(dòng)該Activity時(shí)悠抹,該Activity所在的任務(wù)棧珠月,將會(huì)轉(zhuǎn)移到前臺(tái)。
    可以在不同的程序中共享一個(gè)Activity

異常狀態(tài)

當(dāng)系統(tǒng)資源配置發(fā)生改變或者內(nèi)存不足時(shí)Activity會(huì)被殺死楔敌。

  • 系統(tǒng)配置發(fā)生改變
    系統(tǒng)配置發(fā)生改變Activity會(huì)被殺死重建啤挎,經(jīng)典場(chǎng)景就是橫豎屏切換的時(shí)候。
    此時(shí)的生命周期狀態(tài)轉(zhuǎn)換:
    onSaveInstanceState()->onStop()->onDestory()->onCreate()->onStart()->onRestoreInstanceState()->onResume()->activity runing
    這里出現(xiàn)了兩個(gè)方法
    1.onSaveInstanceState()
    當(dāng)Activity被異常狀態(tài)下終止時(shí)會(huì)調(diào)用該方法來將Activity終止前的相關(guān)狀態(tài)保存在Bundle中用來重建時(shí)恢復(fù)狀態(tài)
    2.onRestoreInstanceState()
    當(dāng)Activity被在異常狀態(tài)下重建時(shí)回調(diào)該方法卵凑,該方法中的Bundle里保存了異常終止前Activity相關(guān)狀態(tài)庆聘。
    此時(shí)可以通過在AndroidManifestl.xml文件中相應(yīng)的activity節(jié)點(diǎn)下配置android:configChanges="orientation|keyboardHidden"屬性來禁止相應(yīng)的配置改變時(shí)activity的銷毀重建。但是此時(shí)會(huì)回調(diào)Activity中的onConfigurationChanged()方法勺卢。
  • 系統(tǒng)內(nèi)存不足
    當(dāng)系統(tǒng)內(nèi)存不足時(shí)伙判,系統(tǒng)將會(huì)根據(jù)activity優(yōu)先級(jí)的高低,優(yōu)先殺死優(yōu)先級(jí)低的Activity黑忱。
    1.此時(shí)的生命周期:
    activity runing->onPause()->onStop()->onDestory()
    2.優(yōu)先級(jí):
    前臺(tái)Activity>可見非前臺(tái)Activity>后臺(tái)Activity

上文代碼


Service

Service 是一個(gè)可以在后臺(tái)執(zhí)行長(zhǎng)時(shí)間運(yùn)行操作而不提供用戶界面的應(yīng)用組件澳腹。服務(wù)可由其他應(yīng)用組件啟動(dòng),而且即使用戶切換到其他應(yīng)用杨何,服務(wù)仍將在后臺(tái)繼續(xù)運(yùn)行酱塔。 此外,組件可以綁定到服務(wù)危虱,以與之進(jìn)行交互羊娃,甚至是執(zhí)行進(jìn)程間通信 (IPC)。 例如埃跷,服務(wù)可以處理網(wǎng)絡(luò)事務(wù)蕊玷、播放音樂,執(zhí)行文件 I/O 或與內(nèi)容提供程序交互弥雹,而所有這一切均可在后臺(tái)進(jìn)行垃帅。

生命周期

service_lifecycle.png

由上圖可知Service有兩種生命周期,分別對(duì)應(yīng)著Service的兩種形式

Service形式

啟動(dòng)形式

????????如果應(yīng)用組件通過startService()方法來啟動(dòng)服務(wù)時(shí)剪勿,該服務(wù)即處于啟動(dòng)狀態(tài)贸诚。
????????服務(wù)處于啟動(dòng)狀態(tài)后將開始在后臺(tái)無期限運(yùn)行,組件被銷毀也不會(huì)影響服務(wù)的運(yùn)行狀態(tài)。并且啟動(dòng)形式的服務(wù)與組件之間沒有很大的關(guān)聯(lián)并不會(huì)將服務(wù)結(jié)果返回給組件酱固。如通過啟動(dòng)一個(gè)服務(wù)來下載網(wǎng)絡(luò)資源械念。
????????啟動(dòng)的服務(wù)可以在組件中通過stopService()或者在服務(wù)內(nèi)部通過stopSelf()方法來停止服務(wù)。
onCreate()
服務(wù)首次被創(chuàng)建時(shí)运悲,系統(tǒng)將會(huì)調(diào)用該方法來進(jìn)行相關(guān)設(shè)置龄减。該方法只有在服務(wù)被創(chuàng)建時(shí)調(diào)用,如果服務(wù)已在運(yùn)行班眯,則該方法不會(huì)調(diào)用希停。
onStartCommand()
組件通過調(diào)用startService()方法啟動(dòng)服務(wù)時(shí),該方法將會(huì)被調(diào)用署隘。該方法被調(diào)用后服務(wù)將會(huì)啟動(dòng)并將在后臺(tái)無限期運(yùn)行宠能,并且需要調(diào)用stopService()或者stopSelf()方法來停止服務(wù)。每次調(diào)用startService()方法都會(huì)該方法都將會(huì)被調(diào)用定踱。在綁定狀態(tài)下不需要實(shí)現(xiàn)這個(gè)方法
onDestory()
當(dāng)服務(wù)不再使用并將被銷毀時(shí),系統(tǒng)將調(diào)用該方法恃鞋。來清理所有的資源崖媚,如線程、監(jiān)聽器恤浪、接收器等畅哑。
onBind()
無論啟動(dòng)服務(wù)還是綁定服務(wù)該方法必須實(shí)現(xiàn)。如果組件通過bindSercie()方法綁定服務(wù)水由,則系統(tǒng)將調(diào)用該方法荠呐,該方法的最后需要一個(gè)IBinder接口的實(shí)現(xiàn)類,用來供組件與服務(wù)進(jìn)行通信砂客。如果組件通過startService()方法來啟動(dòng)服務(wù)則該方法返回null泥张。

綁定形式

????????如果應(yīng)用組件通過bindService()方法綁定到服務(wù)時(shí),該服務(wù)即處于綁定狀態(tài)鞠值。組件與服務(wù)綁定后媚创,綁定服務(wù)提供了一個(gè)客戶端-服務(wù)器接口,允許組件與服務(wù)進(jìn)行交互彤恶、發(fā)送請(qǐng)求钞钙、獲取結(jié)果,甚至是利用進(jìn)程間通信(IPC)跨進(jìn)程執(zhí)行這些操作声离。通俗來講就是綁定服務(wù)后組件和服務(wù)就可以進(jìn)行方法調(diào)用芒炼,增強(qiáng)兩者之間的操作性。
????????組件與服務(wù)綁定后术徊,服務(wù)開始運(yùn)行本刽,一個(gè)服務(wù)可以綁定多個(gè)組件,當(dāng)綁定形式的服務(wù)與任何一個(gè)組件都失去綁定后該服務(wù)會(huì)被銷毀。
????????綁定的服務(wù)可以在組件中通過stopService()或者在服務(wù)內(nèi)部通過stopSelf()方法來停止服務(wù)盅安。
onCreate()
服務(wù)首次被創(chuàng)建時(shí)唤锉,系統(tǒng)將會(huì)調(diào)用該方法來進(jìn)行相關(guān)設(shè)置。該方法只有在服務(wù)被創(chuàng)建時(shí)調(diào)用别瞭,如果服務(wù)已在運(yùn)行窿祥,則該方法不會(huì)調(diào)用。
onBind()
無論啟動(dòng)服務(wù)還是綁定服務(wù)該方法必須實(shí)現(xiàn)蝙寨。如果組件通過bindSercie()方法綁定服務(wù)晒衩,則系統(tǒng)將調(diào)用該方法,該方法的最后需要一個(gè)IBinder接口的實(shí)現(xiàn)類墙歪,用來供組件與服務(wù)進(jìn)行通信听系。如果組件通過startService()方法來啟動(dòng)服務(wù)則該方法返回null
onUnbind()
綁定狀態(tài)的服務(wù)被銷毀時(shí)調(diào)用
onDestory()
當(dāng)服務(wù)不再使用并將被銷毀時(shí)虹菲,系統(tǒng)將調(diào)用該方法靠胜。來清理所有的資源,如線程毕源、監(jiān)聽器浪漠、接收器等。

  • 綁定形式生命周期
    onCreate()->onBind()->Service runing->onUnbind()->onDestroy()

1霎褐、擴(kuò)展Binder類實(shí)現(xiàn)綁定服務(wù)

擴(kuò)展Binder類綁定服務(wù)示例代碼

2址愿、使用AIDL來實(shí)現(xiàn)綁定服務(wù)

使用AIDL來綁定服務(wù)示例代碼

啟動(dòng)服務(wù)與綁定服務(wù)之間的轉(zhuǎn)換問題

一個(gè)服務(wù)可以同時(shí)是啟動(dòng)狀態(tài)和綁定狀態(tài)。但是系統(tǒng)只會(huì)為一個(gè)Service創(chuàng)建一個(gè)實(shí)例對(duì)象冻璃,所以啟動(dòng)服務(wù)和綁定服務(wù)操作的都是同一個(gè)Service實(shí)例响谓,但是由于兩者的執(zhí)行順序不同將會(huì)出現(xiàn)下列兩種情況:

  • 先綁定服務(wù)后啟動(dòng)服務(wù)
    狀態(tài)變化:綁定服務(wù)模式->啟動(dòng)服務(wù)模式
    綁定服務(wù)將會(huì)轉(zhuǎn)換為啟動(dòng)服務(wù)運(yùn)行,此時(shí)如果之前綁定服務(wù)的組件被銷毀也不影響服務(wù)的運(yùn)行省艳。服務(wù)將會(huì)按照啟動(dòng)服務(wù)的模式運(yùn)行娘纷。
  • 先啟動(dòng)服務(wù)后綁定服務(wù)
    狀態(tài)變化:?jiǎn)?dòng)服務(wù)模式
    服務(wù)不會(huì)轉(zhuǎn)換為綁定服務(wù),仍然以啟動(dòng)服務(wù)模式運(yùn)行跋炕。
    但是還是會(huì)與組件綁定失驶,當(dāng)與組件解除綁定之后,對(duì)服務(wù)無影響枣购。

服務(wù)使用注意事項(xiàng)

注意:服務(wù)在其托管進(jìn)程的主線程中運(yùn)行嬉探,它既不創(chuàng)建自己的線程,也不在單獨(dú)的進(jìn)程中運(yùn)行(除非另行指定)棉圈。 這意味著涩堤,如果服務(wù)將執(zhí)行任何 CPU 密集型工作或阻止性操作(例如 MP3 播放或聯(lián)網(wǎng)),則應(yīng)在服務(wù)內(nèi)創(chuàng)建新線程來完成這項(xiàng)工作分瘾。通過使用單獨(dú)的線程胎围,可以降低發(fā)生“應(yīng)用無響應(yīng)”(ANR) 錯(cuò)誤的風(fēng)險(xiǎn),而應(yīng)用的主線程仍可繼續(xù)專注于運(yùn)行用戶與 Activity 之間的交互。

由此可知服務(wù)是托管在進(jìn)程的主線程中運(yùn)行白魂,所以如果服務(wù)要進(jìn)行耗時(shí)或者阻塞性操作汽纤,則應(yīng)該在服務(wù)內(nèi)創(chuàng)建新的線程來完成工作。

  • 建議使用:IntentService
    IntentService是繼承并處理異步請(qǐng)求的一個(gè)類福荸,在IntentService內(nèi)有一個(gè)工作線程來處理耗時(shí)操作

保證服務(wù)不被殺死

  • 因內(nèi)存資源不足被殺死
    可將onStartCommand()方法的返回值設(shè)為START_STICKYSTART_REDELIVER_INTENT蕴坪,該值表示服務(wù)在內(nèi)存資源緊張時(shí)被殺死后,在內(nèi)存資源足夠時(shí)再恢復(fù)敬锐。
    也可將Service設(shè)置為前臺(tái)服務(wù)背传,這樣就有比較高的優(yōu)先級(jí),在內(nèi)存資源緊張時(shí)也不會(huì)被殺掉台夺。
  • 用戶通過 settings -> Apps -> Running -> Stop 方式殺死Service
    該方法會(huì)執(zhí)行Service的生命周期將會(huì)調(diào)用onDestory径玖,所以可以在onDestory()中發(fā)送廣播重新啟動(dòng)Service
    也可以開啟兩個(gè)服務(wù)颤介,相互監(jiān)聽梳星,相互啟動(dòng)。

onStartCommand返回值

  • START_STICKY
    返回此值時(shí)Service被系統(tǒng)kill后滚朵,系統(tǒng)將會(huì)嘗試重新創(chuàng)建Service冤灾,并調(diào)用onStartCommand()方法,如果在此期間沒有新的命令被傳遞到Service則參數(shù)Intentnull
  • START_NOTE_STICKY
    返回值為該值時(shí)始绍,如果Service被系統(tǒng)kill則系統(tǒng)不會(huì)自動(dòng)重啟該服務(wù)
  • START_REDELIVEER_INTENT
    返回此值時(shí)瞳购,如果Service被系統(tǒng)kill殺死话侄,系統(tǒng)將自動(dòng)重啟該服務(wù)亏推,并重新傳遞Intent
  • START_STICKY_COMPATIBILITY
    START_STICKY的兼容版本并不保證kill后一定能重啟
    系統(tǒng)默認(rèn)返回START_STICKY

上文代碼

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市年堆,隨后出現(xiàn)的幾起案子吞杭,更是在濱河造成了極大的恐慌,老刑警劉巖变丧,帶你破解...
    沈念sama閱讀 218,525評(píng)論 6 507
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件芽狗,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡痒蓬,警方通過查閱死者的電腦和手機(jī)童擎,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,203評(píng)論 3 395
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來攻晒,“玉大人顾复,你說我怎么就攤上這事÷衬螅” “怎么了芯砸?”我有些...
    開封第一講書人閱讀 164,862評(píng)論 0 354
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)。 經(jīng)常有香客問我假丧,道長(zhǎng)双揪,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 58,728評(píng)論 1 294
  • 正文 為了忘掉前任包帚,我火速辦了婚禮渔期,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘婴噩。我一直安慰自己擎场,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,743評(píng)論 6 392
  • 文/花漫 我一把揭開白布几莽。 她就那樣靜靜地躺著迅办,像睡著了一般。 火紅的嫁衣襯著肌膚如雪章蚣。 梳的紋絲不亂的頭發(fā)上站欺,一...
    開封第一講書人閱讀 51,590評(píng)論 1 305
  • 那天,我揣著相機(jī)與錄音纤垂,去河邊找鬼矾策。 笑死,一個(gè)胖子當(dāng)著我的面吹牛峭沦,可吹牛的內(nèi)容都是我干的贾虽。 我是一名探鬼主播,決...
    沈念sama閱讀 40,330評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼吼鱼,長(zhǎng)吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼蓬豁!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起菇肃,我...
    開封第一講書人閱讀 39,244評(píng)論 0 276
  • 序言:老撾萬榮一對(duì)情侶失蹤地粪,失蹤者是張志新(化名)和其女友劉穎,沒想到半個(gè)月后琐谤,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體蟆技,經(jīng)...
    沈念sama閱讀 45,693評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,885評(píng)論 3 336
  • 正文 我和宋清朗相戀三年斗忌,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了质礼。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 40,001評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡织阳,死狀恐怖眶蕉,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情陈哑,我是刑警寧澤妻坝,帶...
    沈念sama閱讀 35,723評(píng)論 5 346
  • 正文 年R本政府宣布伸眶,位于F島的核電站,受9級(jí)特大地震影響刽宪,放射性物質(zhì)發(fā)生泄漏厘贼。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,343評(píng)論 3 330
  • 文/蒙蒙 一圣拄、第九天 我趴在偏房一處隱蔽的房頂上張望嘴秸。 院中可真熱鬧,春花似錦庇谆、人聲如沸岳掐。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,919評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽串述。三九已至,卻和暖如春寞肖,著一層夾襖步出監(jiān)牢的瞬間纲酗,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,042評(píng)論 1 270
  • 我被黑心中介騙來泰國(guó)打工新蟆, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留觅赊,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 48,191評(píng)論 3 370
  • 正文 我出身青樓琼稻,卻偏偏與公主長(zhǎng)得像吮螺,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子帕翻,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,955評(píng)論 2 355

推薦閱讀更多精彩內(nèi)容