
Bundle類:豎屏的activity換到橫屏的activity的時候,會把豎屏的activity殺掉橫屏的activity建立,豎屏的activity會有一些計算結果,可以用資料存起來,存到記憶體裡面,然後存在橫屏的activity。
Intent類putExtra("user", user);傳資料的時候用的就是Bundle物件, private Bundle mExtras;
Bundle是一個map,
package com.sxt.day04_03;
import java.io.IOException;
import java.io.InputStream;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLConnection;
import android.app.Activity;
import android.os.Bundle;
import android.util.Log;
public class MainActivity extends Activity {
String mUsers;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Log.i("main","onCreate()");
if(savedInstanceState==null){// 若是第一次建立MainActivity為空
//從服務端下載users.json檔案
downloadUsers();
}else{//
mUsers=savedInstanceState.getString("users");
Log.i("main",mUsers);
}
}
//從服務端下載users.json檔案
private void downloadUsers() {
new Thread(){//sdk從4.0開始要求下載資料必須在工作執行緒中執行不能在主執行緒執行
public void run() {
InputStream in =null;
try {
URL url=new URL("http://10.0.2.2/users.json");
URLConnection conn = url.openConnection();
in = conn.getInputStream();//建立輸入流
byte[] buffer=new byte[1024];//json檔案不到1k,如果很大則每次讀取10k,一次一次的讀。
int len = in.read(buffer);
mUsers=new String(buffer, 0, len);
Log.i("main",mUsers);
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}finally{
if(in!=null){
try {
in.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
};
}.start();
}
@Override
protected void onStart() {
super.onStart();
Log.i("main","onStart()");
}
@Override
protected void onResume() {
super.onResume();
Log.i("main","onResume()");
}
@Override
protected void onPause() {
super.onPause();
Log.i("main", "onPause()");
}
@Override
protected void onStop() {
super.onStop();
Log.i("main","onStop()");
}
@Override
protected void onDestroy() {
super.onDestroy();
Log.i("main","onDestroy()");
}
@Override
protected void onRestart() {
super.onRestart();
Log.i("main","onRestatr()");
}
@Override //儲存activity狀態資料,資料在記憶體中,Bundle型別存著
protected void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
Log.i("main","onSaveInstanceState()");
outState.putString("users", mUsers);
}
@Override //恢復記憶體中的資料
protected void onRestoreInstanceState(Bundle savedInstanceState) {
super.onRestoreInstanceState(savedInstanceState);
Log.i("main","onRestoreInstanceState()");
}
}
當某個activity變得“容易”被系統銷燬時,該activity的onSaveInstanceState就會被執行,除非該activity是被使用者主動銷燬的,例如當用戶按BACK鍵的時候。
注意上面的雙引號,何為“容易”?言下之意就是該activity還沒有被銷燬,而僅僅是一種可能性。這種可能性有哪些?通過重寫一個activity的所有生命週期的onXXX方法,包括onSaveInstanceState和onRestoreInstanceState方法,我們可以清楚地知道當某個activity(假定為activity A)顯示在當前task的最上層時,其onSaveInstanceState方法會在什麼時候被執行,有這麼幾種情況:
1、當用戶按下HOME鍵時。
這是顯而易見的,系統不知道你按下HOME後要執行多少其他的程式,自然也不知道activity A是否會被銷燬,故系統會呼叫onSaveInstanceState,讓使用者有機會儲存某些非永久性的資料。以下幾種情況的分析都遵循該原則
2、長按HOME鍵,選擇執行其他的程式時。
3、按下電源按鍵(關閉螢幕顯示)時。
4、從activity A中啟動一個新的activity時。
5、螢幕方向切換時,例如從豎屏切換到橫屏時。
在螢幕切換之前,系統會銷燬activity A,在螢幕切換之後系統又會自動地建立activity A,所以onSaveInstanceState一定會被執行。
總而言之,onSaveInstanceState的呼叫遵循一個重要原則,即當系統“未經你許可”時銷燬了你的activity,則onSaveInstanceState會被系統呼叫,這是系統的責任,因為它必須要提供一個機會讓你儲存你的資料(當然你不儲存那就隨便你了)。
至於onRestoreInstanceState方法,需要注意的是,onSaveInstanceState方法和onRestoreInstanceState方法“不一定”是成對的被呼叫的,onRestoreInstanceState被呼叫的前提是,activity A“確實”被系統銷燬了,而如果僅僅是停留在有這種可能性的情況下,則該方法不會被呼叫,例如,當正在顯示activity A的時候,使用者按下HOME鍵回到主介面,然後使用者緊接著又返回到activity A,這種情況下activity A一般不會因為記憶體的原因被系統銷燬,故activity A的onRestoreInstanceState方法不會被執行。
另外,onRestoreInstanceState的bundle引數也會傳遞到onCreate方法中,你也可以選擇在onCreate方法中做資料還原。