首页 文章

为什么Kotlin数据类在Gson的非可空字段中可以有空值?

提问于
浏览
1

在Kotlin你可以创建一个 data class

data class CountriesResponse(
    val count: Int,
    val countries: List<Country>,
    val error: String)

然后你可以用它来解析JSON,例如"{n: 10}" . 在这种情况下,您将拥有一个从 RetrofitFuelGson 收到的对象 val countries: CountriesResponse ,其中包含以下值: count = 0, countries = null, error = null .

Kotlin + Gson - How to get an emptyList when null for data class中,您可以看到另一个示例 .

当您稍后尝试使用 countries 时,您将在此处获得异常: val size = countries.countries.size :"kotlin.TypeCastException: null cannot be cast to non-null type kotlin.Int" . 如果您编写代码并在访问这些字段时使用 ? ,Android Studio将突出显示 ?. 并警告: Unnecessary safe call on a non-null receiver of type List<Country> .

那么,我们应该在数据类中使用 ? 吗?为什么应用程序在运行时可以将 null 设置为不可为空的变量?

1 回答

  • 9

    发生这种情况是因为Gson使用不安全(如 java.misc.Unsafe )实例构造机制来创建类的实例,绕过它们的构造函数,然后直接设置它们的字段 .

    有关一些研究,请参阅此问答:Gson Deserialization with Kotlin, Initializer block not called .

    因此,Gson忽略了构造逻辑和类状态不变量,因此不建议将它用于可能受此影响的复杂类 . 它也忽略了setter中的值检查 .

    考虑一个Kotlin感知的序列化解决方案,例如Jackson(在上面链接的Q&A中提到)或kotlinx.serialization .

相关问题