为什么Kotlin数据类在Gson的不可为空的字段中可以具有null? [英] Why Kotlin data classes can have nulls in non-nullable fields with Gson?

查看:851
本文介绍了为什么Kotlin数据类在Gson的不可为空的字段中可以具有null?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在Kotlin中,您可以创建data class:

In Kotlin you can create a 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.

Then you can use it to parse a JSON, for instance, "{n: 10}". In this case you will have an object val countries: CountriesResponse, received from Retrofit, Fuel or Gson, that contains these values: count = 0, countries = null, error = null.

> Kotlin + Gson-数据类为空时如何获取EmptyList ,您可以看到另一个示例.

In Kotlin + Gson - How to get an emptyList when null for data class you can see another example.

稍后当您尝试使用countries时,将在此处获得异常:val size = countries.countries.size:"kotlin.TypeCastException:不能将null强制转换为非null类型的kotlin.Int".如果您编写代码并在访问这些字段时使用?,则Android Studio将突出显示?.并发出警告:Unnecessary safe call on a non-null receiver of type List<Country>.

When you later try to use countries, you will get an exception here: val size = countries.countries.size: "kotlin.TypeCastException: null cannot be cast to non-null type kotlin.Int". If you write a code and use ? when accessing these fields, Android Studio will highlight ?. and warn: Unnecessary safe call on a non-null receiver of type List<Country>.

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

So, should we use ? in data classes? Why can an application set null to non-nullable variables during runtime?

推荐答案

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

This happens because Gson uses an unsafe (as in java.misc.Unsafe) instance construction mechanism to create instances of classes, bypassing their constructors, and then sets their fields directly.

有关此研究的信息,请参见此问答:>用Kotlin进行Gson反序列化,初始化程序块未调用.

See this Q&A for some research: Gson Deserialization with Kotlin, Initializer block not called.

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

As a consequence, Gson ignores both the construction logic and the class state invariants, so it is not recommended to use it for complex classes which may be affected by this. It ignores the value checks in the setters as well.

考虑一种支持Kotlin的序列化解决方案,例如Jackson(在上面的Q& A中提到)或 kotlinx.serialization .

Consider a Kotlin-aware serialization solution, such as Jackson (mentioned in the Q&A linked above) or kotlinx.serialization.

这篇关于为什么Kotlin数据类在Gson的不可为空的字段中可以具有null?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆