作為android開發(fā)者都知道,開發(fā)中具備兩種序列化的操作惠拭,一個是Serializable扩劝,另一個是在Android中引入的Parcelable庸论;從google官網(wǎng)的態(tài)度而言,Parcelable的效率更高棒呛。但是兩者的實現(xiàn)方式卻有很大區(qū)別聂示,舉個例子
Serializable
class Human:Serializable {
}
Parcelable
class Person() :Parcelable {
var name:String = ""
var age:Int = 0
constructor(parcel: Parcel) : this() {
}
override fun describeContents(): Int {
return 0
}
override fun writeToParcel(dest: Parcel, flags: Int) {
dest.writeString(name)
dest.writeInt(age)
}
companion object CREATOR : Parcelable.Creator<Person> {
override fun createFromParcel(parcel: Parcel): Person {
val person = Person()
person.name = parcel.readString()?:""
person.age = parcel.readInt()?:0
return person
}
override fun newArray(size: Int): Array<Person?> {
return arrayOfNulls(size)
}
}
}
發(fā)現(xiàn)什么問題了嗎?沒錯簇秒,Percelable的實現(xiàn)方式更復(fù)雜鱼喉,Serializable只需實現(xiàn)一個接口就完成了,管他那么多趋观,Serializable就完事了(這也是我至今都喜歡Serializable的原因)
后面在閱讀官方文檔的時候扛禽,發(fā)現(xiàn)Percelable也有了簡單的方式,而且官方也是推薦使用 Percelable皱坛,所以還是更改了使用習(xí)慣编曼,而且,新的方式也很簡單點擊跳轉(zhuǎn)
1.Parcelable 實現(xiàn)生成器
首先引入組件
plugins {
id 'kotlin-parcelize'
}
實現(xiàn)類主體結(jié)構(gòu)
import kotlinx.parcelize.Parcelize
@Parcelize
class User(val firstName: String, val lastName: String, val age: Int): Parcelable
2.自定義序列化邏輯
有的同學(xué)就會問了剩辟,如果我想自己寫序列化和反序列化邏輯呢掐场?當(dāng)然也有辦法,就是在類內(nèi)部實現(xiàn)write和create方法
@Parcelize
data class User(val firstName: String, val lastName: String, val age: Int) : Parcelable {
private companion object : Parceler<User> {
override fun User.write(parcel: Parcel, flags: Int) {
// Custom write implementation
}
override fun create(parcel: Parcel): User {
// Custom read implementation
}
}
}
3.Parcelable 支持的類型
應(yīng)該說大部分的類型就是支持贩猎,但是如果真遇到了某個類型不被支持熊户,但是開發(fā)者就是想要序列化,Parcelable也有自定義的方法吭服,就是
class ExternalClass(val value: Int)
object ExternalClassParceler : Parceler<ExternalClass> {
override fun create(parcel: Parcel) = ExternalClass(parcel.readInt())
override fun ExternalClass.write(parcel: Parcel, flags: Int) {
parcel.writeInt(value)
}
}
使用也很方便
// Class-local parceler
@Parcelize
@TypeParceler<ExternalClass, ExternalClassParceler>()
class MyClass(val external: ExternalClass) : Parcelable
// Property-local parceler
@Parcelize
class MyClass(@TypeParceler<ExternalClass, ExternalClassParceler>() val external: ExternalClass) : Parcelable
// Type-local parceler
@Parcelize
class MyClass(val external: @WriteWith<ExternalClassParceler>() ExternalClass) : Parcelable
簡單也易上手嚷堡,但是也溫馨提醒,大量數(shù)據(jù)跨組件傳遞噪馏,會存在為以下情況
因為intent中能帶的數(shù)據(jù)有上限(這個根據(jù)不同的android廠商而異)麦到,建議這時候試用viewmodel來做數(shù)據(jù)傳遞