Kotlin 序列化库 kotlinx.serialization 是一个强大的工具,可用于序列化和反序列化复杂的数据结构。
1,首先需要添加依赖
在模块级的build.gradle.kts(:app)中:
scss
plugins {
......
// 下面代码中version中代码中Kotlin的版本号
kotlin("plugin.serialization") version "2.0.0"
}
dependencies {
......
implementation(libs.serialization.json)
......
}
在libs.versions.toml文件中:
ini
[versions]
serialization-json = "1.8.1"
[libraries]
serialization-json = { group = "org.jetbrains.kotlinx", name = "kotlinx-serialization-json", version.ref = "serialization-json"}
2,定义可序列化的数据结构
要确保数据结构的类被 @Serializable 注解标记。
kotlin
import kotlinx.serialization.Serializable
@Serializable
data class Person(
val name: String,
val age: Int,
val address: Address,
val hobbies: List<String>
)
@Serializable
data class Address(
val street: String,
val city: String,
val zipCode: String
)
3,序列化数据结构
借助 kotlinx.serialization.json.Json 类的 encodeToString 方法,能够将对象序列化为 JSON 字符串。
kotlin
import kotlinx.serialization.encodeToString
import kotlinx.serialization.json.Json
fun main() {
val address = Address("123 Main St", "Anytown", "12345")
val person = Person("John Doe", 30, address, listOf("Reading", "Running"))
val jsonString = Json.encodeToString(person)
println("Serialized JSON: $jsonString")
}
4,反序列化数据结构
使用 kotlinx.serialization.json.Json 类的 decodeFromString 方法,可将 JSON 字符串反序列化为对象。
javascript
import kotlinx.serialization.decodeFromString
import kotlinx.serialization.json.Json
fun main() {
val jsonString = """
{
"name": "John Doe",
"age": 30,
"address": {
"street": "123 Main St",
"city": "Anytown",
"zipCode": "12345"
},
"hobbies": ["Reading", "Running"]
}
""".trimIndent()
val person = Json.decodeFromString<Person>(jsonString)
println("Deserialized Person: $person")
}
5, 处理嵌套集合等复杂情况
若数据结构包含嵌套集合,序列化和反序列化的过程是一样的。
kotlin
import kotlinx.serialization.Serializable
import kotlinx.serialization.encodeToString
import kotlinx.serialization.decodeFromString
import kotlinx.serialization.json.Json
@Serializable
data class School(
val name: String,
val classes: List<ClassRoom>
)
@Serializable
data class ClassRoom(
val grade: Int,
val students: List<Student>
)
@Serializable
data class Student(
val name: String,
val age: Int
)
fun main() {
val student1 = Student("Alice", 12)
val student2 = Student("Bob", 13)
val classRoom = ClassRoom(6, listOf(student1, student2))
val school = School("ABC School", listOf(classRoom))
val jsonString = Json.encodeToString(school)
println("Serialized JSON: $jsonString")
val deserializedSchool = Json.decodeFromString<School>(jsonString)
println("Deserialized School: $deserializedSchool")
}
6,自定义序列化器
在某些情况下,默认的序列化器可能无法满足需求,这时可以自定义序列化器。
kotlin
// 导入 kotlinx.serialization 库的所有基础类和注解,这些是实现序列化和反序列化功能的核心。
import kotlinx.serialization.*
// 用于表示基本数据类型的枚举类,在定义序列化描述符时会用到。
import kotlinx.serialization.descriptors.PrimitiveKind
// 用于创建基本数据类型的序列化描述符
import kotlinx.serialization.descriptors.PrimitiveSerialDescriptor
// 序列化描述符的接口,描述了数据类型的结构,序列化和反序列化过程中会用到。
import kotlinx.serialization.descriptors.SerialDescriptor
// 用于从输入流中读取数据并将其转换为对象的接口,在反序列化时使用。
import kotlinx.serialization.encoding.Decoder
// 用于将对象转换为输出流的接口,在序列化时使用。
import kotlinx.serialization.encoding.Encoder
// 用于处理 JSON 格式的序列化和反序列化的类。
import kotlinx.serialization.json.Json
//@Serializable(with = CustomDateSerializer::class):
// 这是一个序列化注解,表明 Event 类是可序列化的。
// with 参数指定了使用自定义的序列化器 CustomDateSerializer 来处理 Event 类中的 date 字段。
@Serializable(with = CustomDateSerializer::class)
// 定义了一个名为 Event 的数据类,包含两个属性:name(字符串类型)和 date(java.util.Date 类型)。
data class Event(val name: String, val date: java.util.Date)
// 使用 object 关键字定义了一个单例对象 CustomDateSerializer,
// 它实现了 KSerializer<java.util.Date> 接口,用于处理 java.util.Date 类型的序列化和反序列化。
object CustomDateSerializer : KSerializer<java.util.Date> {
// override val descriptor 重写了 KSerializer 接口中的 descriptor 属性, 用于描述序列化的数据类型。
// 这里使用 PrimitiveSerialDescriptor 创建了一个描述符,表明 Date 类型将被序列化为一个长整型(PrimitiveKind.LONG)。
override val descriptor: SerialDescriptor = PrimitiveSerialDescriptor("Date", PrimitiveKind.LONG)
// 重写了 KSerializer 接口中的 serialize 方法,用于将 java.util.Date 对象序列化为长整型。
override fun serialize(encoder: Encoder, value: java.util.Date) {
// 使用 Encoder 对象的 encodeLong 方法将 Date 对象的时间戳(通过 value.time 获取)写入输出流。
encoder.encodeLong(value.time)
}
// 重写了 KSerializer 接口中的 deserialize 方法,用于从输入流中读取长整型数据并将其转换为 java.util.Date 对象。
override fun deserialize(decoder: Decoder): java.util.Date {
// 使用 Decoder 对象的 decodeLong 方法从输入流中读取长整型数据,然后将其作为参数传递给 java.util.Date 的构造函数,创建一个新的 Date 对象。
return java.util.Date(decoder.decodeLong())
}
}
fun main() {
// 创建了一个 Event 对象,name 属性为 "Conference",date 属性为当前时间。
val event = Event("Conference", java.util.Date())
// 使用 Json 类的 encodeToString 方法将 Event 对象序列化为 JSON 字符串。
val jsonString = Json.encodeToString(event)
println("Serialized JSON: $jsonString")
// 使用 Json 类的 decodeFromString 方法将 JSON 字符串反序列化为 Event 对象。
val deserializedEvent = Json.decodeFromString<Event>(jsonString)
println("Deserialized Event: $deserializedEvent")
}