Android開發——通過 Intent 傳遞類物件
在android開發中,經常會使用Intent來傳遞資料,在Google官方的android api中對於基本資料型別,Intent類中都有對應的方法 intent.putExtra(key,date);來傳遞資料
然而在實際開發中,基本資料型別肯定是不能夠滿足需要的,這個時候怎麼辦?對於自定義的類物件,如何通過Intent來傳遞呢?
這個時候就需要將物件序列化(Serializable)後才能傳遞,那麼問題來了,
一、什麼是序列化呢?
通俗的來說就是把一個物件按照順序排列成位元組序列,個人感覺有點類似於網路視訊按照視訊流進行流媒體傳輸的道理,視訊檔案本身佔空間相對較大,不適合網路傳輸,但是如果將視訊按照播放先後順序壓縮成流媒體,一幀幀的傳輸(實際基於TCP/IP協議的網路是分資料包傳輸,每個資料包傳輸數幀,不止一幀),就完全可以傳輸過去了,同樣的道理,Intent是無法傳輸物件的,但是將物件序列化之後就不一樣了。
二、那到底怎麼序列化一個物件?
主要有兩種方法
- 一種是實現Serializable介面(是JavaSE本身就支援的)
- 另一種是實現Parcelable介面(是Android特有功能,效率比實現Serializable介面高效,可用於Intent資料傳遞,也可以用於程序間通訊(IPC))
具體操作如下:
1.通過實現Serializable介面將物件序列化
程式碼如下:
public class Person implements Serializable
{
//這裡定義個serialVersionUID用於進行序列化和反序列化後資料比對
private static final long serialVersionUID = -1111L;
private String name;
private int age;
public String getName()
{
return name;
}
public void setName(String name)
{
this.name = name;
}
public int getAge()
{
return age;
}
public void setAge(int age)
{
this.age = age;
}
}
只需要將要傳遞的類物件implements Serializable,然後定義個serialVersionUID常量即可,然後就可以任性的用
intent.putExtra("person",person);
傳遞person物件,這主要是得益於android原始碼中有序列化物件的過載方法,下方該過載方法的android原始碼:
/**
* Add extended data to the intent. The name must include a package
* prefix, for example the app com.android.contacts would use names
* like "com.android.contacts.ShowAll".
*
* @param name The name of the extra data, with package prefix.
* @param value The Serializable data value.
*
* @return Returns the same Intent object, for chaining multiple calls
* into a single statement.
*
* @see #putExtras
* @see #removeExtra
* @see #getSerializableExtra(String)
*/
public Intent putExtra(String name, Serializable value) {
if (mExtras == null) {
//從這裡可以看出Intent傳遞資料,其實是用的Bundle(本文作者加的註釋,原始碼沒有這行)
mExtras = new Bundle();
}
mExtras.putSerializable(name, value);
return this;
}
2.第二種方法是實現Parcelable介面將物件序列化:
剛剛的Serializable在序列化的時候是將整個物件進行序列化,而Parcelable 方式的實現原理是將一個完整的物件進行分解,而分解後的每一部分都是Intent 所支援的資料型別,這樣也就實現傳遞物件的功能了。
這個相對複雜,先來看看介面定義:
public interface Parcelable
{
//內容描述介面,基本不用管
public int describeContents();
//寫入介面函式,打包
public void writeToParcel(Parcel dest, int flags);
//讀取介面,目的是要從Parcel中構造一個實現了Parcelable的類的例項處理。因為實現類在這裡還是不可知的,所以需要用到模板的方式,繼承類名通過模板引數傳入
//為了能夠實現模板引數的傳入,這裡定義Creator嵌入介面,內含兩個介面函式分別返回單個和多個繼承類例項
public interface Creator<T>
{
public T createFromParcel(Parcel source);
public T[] newArray(int size);
}
}
只看介面定義可能很暈,下面來看看具體實現步驟:
1. implements Parcelable
2. 重寫writeToParcel方法,將你的物件序列化為一個Parcel物件,即:將類的資料寫入外部提供的Parcel中,打包需要傳遞的資料到Parcel容器儲存,以便從 Parcel容器獲取資料
3. 重寫describeContents方法,內容介面描述,預設返回0就可以
4. 例項化靜態內部物件CREATOR實現介面Parcelable.Creator
public static final Parcelable.Creator<T> CREATOR
注:其中public static final一個都不能少,內部物件CREATOR的名稱也不能改變,必須全部大寫。需重寫本介面中的兩個方法:createFromParcel(Parcel in) 實現從Parcel容器中讀取傳遞資料值,封裝成Parcelable物件返回邏輯層,newArray(int size) 建立一個型別為T,長度為size的陣列,僅一句話即可(return new T[size]),供外部類反序列化本類陣列使用。
簡單說就是通過writeToParcel將你的物件拆解對映成Parcel物件,再通過createFromParcel將Parcel物件組裝對映成你的物件。這個過程很想我剛剛提到的流媒體傳輸,可以將Parcel看成是一個流,通過writeToParcel把物件寫到流裡面,在通過createFromParcel從流裡讀取物件,只不過這個過程需要你來實現,因此寫的順序和讀的順序必須一致。
implements Parcelable實現的person類如下:
public class Person implements Parcelable
{
private String name;
private int age;
public String getName()
{
return name;
}
public void setName(String name)
{
this.name = name;
}
public int getAge()
{
return age;
}
public void setAge(int age)
{
this.age = age;
}
@Override
public int describeContents()
{
return 0;
}
@Override
public void writeToParcel(Parcel out, int flags)
{
out.writeString(name);
out.writeString(age);
}
public static final Parcelable.Creator<Person> CREATOR = new Creator<Person>()
{
@Override
public Person[] newArray(int size)
{
return new Person[size];
}
@Override
public Person createFromParcel(Parcel in)
{
Person person=new Person();
person.name=in.readString();
person.age=in.readInt();
return person;
}
};
public Person(Parcel in)
{
name= in.readString();
age= in.readString();
}
}
三、序列化的作用:
1)永久性儲存物件,儲存物件的位元組序列到本地檔案中;
2)通過序列化物件在網路中傳遞物件;
3)通過序列化在程序間傳遞物件。
四、兩種方法的比較:
1)在使用記憶體的時候,Parcelable比Serializable效能高,所以推薦使用Parcelable。
2)Serializable在序列化的時候會產生大量的臨時變數,從而引起頻繁的Gabage Collection,導致效能的下降。
3)Parcelable不能使用在要將資料儲存在磁碟上的情況,因為在外界有變化的情況下,Parcelable不能很好的保證資料的持續性。儘管Serializable效率低點,但此時還是建議使用Serializable
相關推薦
Android開發——通過 Intent 傳遞類物件
在android開發中,經常會使用Intent來傳遞資料,在Google官方的android api中對於基本資料型別,Intent類中都有對應的方法 intent.putExtra(key,date);來傳遞資料 然而在實際開發中,基本資料型別肯定是不能夠
Android 通過 Intent 傳遞類物件
Android中通過 Intent傳遞類物件 1.通過實現Serializable介面傳遞物件(必須實現該介面) 2.通過實現Parcelable介面傳遞物件(必須實現該介面) Bundle.put
Android中Intent傳遞類物件的方法一(Serializable)
Activity之間通過Intent傳遞值,支援基本資料型別和String物件及它們的陣列物件byte、byte[]、char、char[]、boolean、boolean[]、short、short[]、int、int[]、long、long[]、float、
Android開發——使用intent傳遞對象
style 開發 start result oid conda .html cond spa intent傳遞對象有兩種方法: 方式一:Serializable 方式 方式二:Parcelable方式 在這裏不多介紹了,這一篇就是快速上手使用教程,至於詳細原理介紹的,
Android開發使用Intent傳遞複雜資料(List集合,Map等)
Intent(意圖)在Android開發中是用於在各個Activity之間傳輸資料用的。它可傳輸的資料形式主要有以下幾種:1、簡單資料。(使用Bundle即可)2、陣列。3、List集合。4、Map<String, Object>。(可以放在一個List集合裡傳輸
說說如何使用 Android 中的 Intent 來傳遞類物件
使用 Intent 來傳遞物件有兩種方式:Serializable 和 Parcelable。 1 Serializable 方式 假設有一個 POJO 的 Account 類,該類實現了 Serializable 介面: public class Account im
android 利用intent傳遞含有物件的list
做demo的時候發現要用到intent傳遞一個Object型別的list。方法也很簡單,先將Object類Serializable,然後Intent傳list時強轉成Serializable型別例:i
Android開發筆記之工具類使用靜態方法與單例物件方法的優劣
最近在做專案開發的時候用到了很多工具類,之前對工具類的理解僅限於使用靜態方法,沒有細究.寫了很多有損app執行效能的程式碼.例如在靜態方法內建立了例項物件,這樣讓靜態方法持有物件,使得物件一直存在與記憶體中,無法被GC回收,佔用記憶體,影響效能和使用者體驗
Android通過Intent傳遞資料
日常開發中,我們經常遇到通過 Intent 來傳遞資料,預設情況,我們可以看到支援的資料型別: 基本型別:boolean、byte、char 、short、double、float、int、long 字串型別:String、String[]、CharSe
通過Intent傳遞物件,已Map為例
對於物件在Activity中的傳遞我們仍然可以使用Intent來實現,只是要在傳遞之前需要將Map強制轉化為Serialzable型別(對於自定義的類我們也可以讓其實現Serializable介面)來實現。 private Map<String, String>
android開發學習 ------- RecyclerView多類型實例
靜態 mco gho add ren dom ble notify 布局 實現RecyclerView多類型的實例:效果如下圖所示 public class CarFragment extends Fragment{ private View view;
動態載入Dll時,通過Type生成類物件
原文: 動態載入Dll時,通過Type生成類物件 轉:http://www.cnblogs.com/zfanlong1314/p/4197383.html “反射”其實就是利用程式集的元資料資訊。 反射可以有很多方法,編寫程式時請先匯入 System.Reflection 名稱空間。
Android開發通過adapter顯示listview
首先,定義一個adapter繼承於某個ArrayAdapter,例項化adapter時將要顯示的peers傳遞進去,然後通過listview.setadapter(new adapter)顯示, getview()方法決定每個item包含的資訊與顯示 adapter = new WiF
Activity中通過Intent傳遞HashMap集合
對於物件在Activity中的傳遞我們仍然可以使用Intent來實現,只是要在傳遞之前需要將Map強制轉化為Serialzable型別(對於自定義的類我們也可以讓其實現Serializable介面)來實
Android開發中資料傳遞大集合
眾所周知,Android開發中資料傳遞方式多種多樣,根據不同的用途需要選擇不同的傳遞方式。作為剛接觸Android才一年的freshman來說,第一次寫部落格還是有點緊張的,嘿嘿。好咯,言歸正傳,進入正題。 據我目前瞭解,資料傳遞方式有 (1)最基本的
[Android開發] Json解析工具類,一個類搞定Json的解析
一、簡介 利用遞迴的方式反射解析到bean裡面 二、詳細程式碼 1、 Json格式 例如伺服器指定規定json格式為: { "code": "……" , // 返回代號,預留欄位,預設返回null "type":"ER
Android開發學習之TypedArray類
在學習Android的開發中,學習Gallery檢視顯示圖片的過程中,在設定圖片介面卡的時候,用到了此TypedArray型別,這次根據android SDK,一塊把此型別弄清楚! android.content.res.TypedArray
Android 最全 Intent 傳遞資料姿勢
點選上面藍色字型關注“IT大飛說” 置頂公眾號(ID:ITBigFly)第一時間收到推送 作為一個 Android 開發人員,我們都是用過 Intent,用它來在元件之間傳遞資料,所以說 Intent 是元件之間通訊的使者,一般情況下,我們傳遞的都
Android開發實現HttpClient工具類以及HttpClient的3種超時說明
引子 在Android開發中我們經常會用到網路連線功能與伺服器進行資料的互動,為此Android的SDK提供了Apache的HttpClient來方便我們使用各種Http服務。你可以把HttpClient想象成一個瀏覽器,通過它的API我們可以很方便的發出GET,POST請求(當然它的功能遠不止這些)。
Android開發 通過JNI實現JAVA與C/C++程式間的呼叫和回撥
在一些Android應用的開發中,需要通過JNI和 Android NDK工具實現JAVA和C/C++之間的相互呼叫。 Java Native Interface (JNI)標準是java平臺的一部分,它允許Java程式碼和其他語言寫的程式碼進行