我要做 Android 第二彈
大家好夏块,這里是我要做 Android 的第二彈疏咐,說實話纤掸,大四了在學(xué)校上課都沒什么心情了。真的是有些焦慮了浑塞,要不是最近在跟著老師做項目借跪,我覺得我就要進入瘋狂找工作模式了。我一直想從事 Android 開發(fā)工作酌壕,這個目標在大二的時候就決定了掏愁。我愿一往無前。不過看了面試題目我決定還是先復(fù)(預(yù))習(xí)吧卵牍。果港。。
話不多說糊昙,開干:
今天我們說 Activity 的 onSaveInstanceState() 和 onRestoreInstanceState() 方法辛掠。我在我的上一篇文章中已經(jīng)詳細的介紹了有關(guān) Activity 的生命周期和方法,如果想了解的可以去看看這篇文章:http://www.reibang.com/p/e246d20f5dd9溅蛉。所以我們可以明確這兩個方法不是生命周期的方法公浪,這是什么意思。
其實在activity的一個生命周期中船侧,onSaveInstanceState() 你不一定能遇得到欠气。
正如官網(wǎng)對該方法的解釋所說:“This method is called before an activity may be killed so that when it comes back some time in the future it can restore its state. ” 在“可能被系統(tǒng)殺死”之前調(diào)用。說的很準確啊镜撩,先明白一點:如果一個 activityA 不可能在后臺被系統(tǒng)主動kill掉预柒,那么就不會調(diào)用該方法
那么回過頭,什么時候activity“可能被系統(tǒng)殺死”呢袁梗?官網(wǎng)也是有明確說明的:
總結(jié)說就是:
onResume() 不會被殺宜鸯。前臺應(yīng)用,系統(tǒng)是不會主動 kill 的遮怜。(廢話淋袖,不能見誰都 kill 吧是吧,你以為你是社會我龍哥嗎锯梁。即碗。。)
onPause() HONEYCOMB(android3.0)之前陌凳,可能被殺剥懒;3.0之后不會被殺。
onStop() 可能被殺合敦。(俗話說見面三分情初橘,我都看不見你了那就管不了這么多了是吧)
明確activity可能在生命周期中被殺的方法之后,根據(jù)上邊說明便可知:
android3.0之前:onResume() -- [optional] onSaveInstanceState() -- onPause(),即調(diào)用onPause()之前,可能調(diào)用 onSaveInstanceState()
android3.0之后:onResume() -- onPause() -- [optional] onSaveInstanceState() -- onStop(), 即調(diào)用onStop()之前保檐,可能調(diào)用 onSaveInstanceState()
如上邊特意提到一樣耕蝉,這里仍要注意“可能”,如果一個 activityA 不可能在后臺被系統(tǒng)主動 kill 掉夜只,那么就不會調(diào)用該方法赔硫。
比如以下邏輯:
activityA.startActivity(activityB)
activityA.finish()
A啟動了B,但是A自己把自己 finish 了盐肃,也就是說系統(tǒng)不可能主動 kill activityA 了爪膊,因此雖然 A 的 onPause()、onStop() 被調(diào)用砸王,但 onSaveInstanceState() 方法也是不會調(diào)用到的推盛。
那么同理,默認情況下在一個activity中谦铃,返回退出也是不會調(diào)用 onSaveInstanceState() 的耘成。(系統(tǒng)表示這個鍋我不背,都是用戶的錯驹闰,誰知道用戶會這樣操作是吧瘪菌。。嘹朗。)
所以總結(jié)下大致的常見的幾種情況:
1师妙、當用戶按下HOME鍵時。
這是顯而易見的屹培,系統(tǒng)不知道你按下 HOME 后要運行多少其他的程序默穴,自然也不知道 activityA 是否會被銷毀,所以系統(tǒng)會調(diào)用 onSaveInstanceState褪秀,讓用戶有機會保存某些非永久性的數(shù)據(jù)蓄诽。以下幾種情況的分析都遵循該原則
2、長按HOME鍵媒吗,選擇運行其他的程序時仑氛。
3、按下電源按鍵(關(guān)閉屏幕顯示)時闸英。
4锯岖、從activity A中啟動一個新的 activity 時。
5自阱、屏幕方向切換時嚎莉,例如從豎屏切換到橫屏?xí)r米酬。
在屏幕切換之前沛豌,系統(tǒng)會銷毀 activity A,在屏幕切換之后系統(tǒng)又會自動地創(chuàng)建 activity A,所以onSaveInstanceState 一定會被執(zhí)行加派。這個在 Android開發(fā)藝術(shù)探索 里介紹的比較詳細叫确。而且還有 demo(可以想一下如果不是系統(tǒng)給我們保存了信息為啥你旋轉(zhuǎn)屏幕后還會出現(xiàn)之前你在看的界面和你正在編輯的未完成的信息呢是吧。 系統(tǒng):這都是我做的芍锦,厲不厲害竹勉,沒我不行吧。娄琉。次乓。所以不要肆意(操)玩(做)弄我。孽水。)
總而言之票腰,onSaveInstanceState 的調(diào)用遵循一個重要原則,即當系統(tǒng) “未經(jīng)你許可” 時銷毀了你的activity女气,則onSaveInstanceState 會被系統(tǒng)調(diào)用杏慰,這是系統(tǒng)的責(zé)任,因為它必須要提供一個機會讓你保存你的數(shù)據(jù)(當然你不保存那就隨便你了)炼鞠。 ———劃重點劃重點劃重點 缘滥。。
Q:onSaveInstanceState() 與 onPause() 的區(qū)別谒主?
有時候會出現(xiàn)這樣的問題朝扼,童鞋們還記得我開頭咋說的嘛,onPause 是在 Activity 不可見的時候調(diào)用霎肯,一般之后就會調(diào)用 onStop 方法吟税,這是生命周期方法。就像人都會經(jīng)過 幼兒 -- 少年 -- 青少年 -- 成年 -- 老年 -- 死亡 一樣姿现,躲不開的肠仪。但 onSaveInstanceState 方法不一樣,它是由系統(tǒng)調(diào)用而不是程序員們調(diào)用备典。具體的發(fā)生時機也不能確定异旧。作用是保存實例狀態(tài),相信我在上面已經(jīng)介紹的很詳細了提佣。
系統(tǒng)異常終止時吮蛹,調(diào)用onSavaInstanceState來保存狀態(tài)。該方法調(diào)用在onStop之前拌屏,但和onPause沒有時序關(guān)系潮针。
onSaveInstanceState 與 onPause 的區(qū)別: 前者適用于對臨時性狀態(tài)的保存,而后者適用于對數(shù)據(jù)的持久化保存倚喂。
Activity被重新創(chuàng)建時每篷,調(diào)用 onRestoreInstanceState(該方法在 onStart 之后)瓣戚,并將onSavaInstanceState保存的Bundle對象作為參數(shù)傳到 onRestoreInstanceState 與onCreate 方法。
可通過 onRestoreInstanceState(Bundle savedInstanceState) 和 onCreate((Bundle savedInstanceState) 來判斷Activity是否被重建焦读,并取出數(shù)據(jù)進行恢復(fù)子库。但需要注意的是,在 onCreate 取出數(shù)據(jù)時一定要先判斷 savedInstanceState 是否為空矗晃。另外仑嗅,谷歌更推薦使用 onRestoreInstanceState 進行數(shù)據(jù)恢復(fù)。