一、概念
进行 Android 开发时,无法将对象的引用传给Activity 或 Fragments,需要将这些对象放到一个 Bundle(Intent)里面然后再传递,而方法中支持的数据类型是有限的(基本数据类型、String),当需要传递自定义对象的时候就需要序列化。
序列化就是将对象转换为可以在网络上传输或者保存到本地的二进制流(二进制序列)的过程,反序列化就是从二进制流(序列)转化为对象的过程。
| Parcelable | Serializable | |
| 性能 | 极快(Android专用,快10倍以上,更紧凑的二进制表示占用内存少) | 较慢(使用反射,会产生大量临时对象占用内存) |
| 实现复杂度 | 复杂(需要手动实现逻辑,可自由控制需要的字段) | 简单(实现 Serializable 接口直接自动把对象全部字段序列化,因此效率低一些) |
| 简单(使用注解的方式直接自动把整个对象序列化) | ||
| 安全性 | 可以序列化部分字段更易控制,字段变化时编译器会报错,手动实现逻辑便于处理字段增减。非通用型机制,仅针对Android通信(IPC、Intent),不要用于磁盘存储或网络传输。 | 字段增减会导致兼容性问题,全部字段序列化可能包含不需要的字段或敏感数据。与其它Java库、网络通信、磁盘存储时使用。 |
二、Serializable
class Person : Serializable {
var name = ""
var age = 0
}
//传递
OneActivity {
val person = Person().apply {
name = "张三"
age = 18
}
Intent(this, TwoActivity::class.java).also {
it.putExtra("person", person)
startActivity(it)
}
}
//获取
TwoActivity {
val person = intent.getSerializableExtra("person") as Person //反序列化成对象
}
三、Parcelable
将一个对象进行分解,分解后的每一个属性都是 Intent 所支持的数据类型。
3.1 实现方式 (不推荐)
创建一个类实现 Parcelable 接口,定义好属性,按 ctrl+1 编译器会自动帮我们生成。
- 实现 Parcelable 接口,重写 describeContents() 和 writeToParcel() 两个函数。describeContents() 直接返回 0 就行。writeToParcel() 调用 writeXXX() 将类中属性一一写入。
- 创建一个名为 CREATOR 的伴生对象实现 Parcelable.Creator 接口,将泛型类型指定为<Person>,重写 createFromParcel() 和 newArray() 两个函数。createFromParcel()中创建一个 Person 对象返回,并调用 readXXX() 将之前写入的属性一一读出(注意读写的顺序要一致)。newArray()中调用 arrayOfNulls() 传入形参 size 作为数组大小即可。
class Person() : Parcelable {
var name = ""
var age = 0
//从 Parcel 读取数据的构造函数
constructor(parcel: Parcel) : this() {
name = parcel.readString() ?: ""
age = parcel.readInt()
}
//写入数据到 Parcel
override fun writeToParcel(parcel: Parcel, flags: Int) {
parcel.writeString(name)
parcel.writeInt(age)
}
//内容描述(通常返回0)
override fun describeContents(): Int {
return 0
}
//创建 Creator 伴生对象实现接口
companion object CREATOR : Parcelable.Creator<Person> {
//返回对象
override fun createFromParcel(parcel: Parcel): Person {
return Person(parcel)
}
//返回一个数组,形参 size 作为数组大小
override fun newArray(size: Int): Array<Person?> {
return arrayOfNulls(size)
}
}
}
//传递方式和 Serializable 一样,使用如下:
TwoActivity {
val person = intent.getParcelableExtra("person")
}
3.2 注解方式 (推荐)
Kotlin提供了更简便的写法,既获得性能又保持简洁。传递的属性都需要定义在主构造中。
//Module Gradle 引入插件
plugins {
id 'kotlin-parcelize'
}
//使用
@Parcelize
class Person(val name: String, var age: Int) : Parcelable
本文介绍了Android开发中如何进行对象序列化,包括Serializable接口的使用以及Parcelable接口的两种实现方式:传统手动实现和注解方式。Parcelable虽然效率更高,但实现相对复杂,而Serializable虽然效率较低,但实现更简单。通过序列化,开发者可以将对象在Activity或Fragments间传递。
1606

被折叠的 条评论
为什么被折叠?



