Kotlin-扩展功能和平台类型?
我想将两个扩展函数添加到ResultSet
,获得一个LocalDate
值。
fun ResultSet.getLocalDate(colName: String) = getDate(colName)?.toLocalDate() fun ResultSet.getLocalDate(colIndex: Int) = getDate(colIndex)?.toLocalDate()
问题是getDate()
返回一个Date!
,显然我可以得到一个空错误没有?.
在toLocalDate()
之前调用。 但是,那么使用这个扩展的任何人都必须使用结果作为LocalDate?
而不是LocalDate!
。
为了一致性,有没有办法维护平台类型? 让扩展函数的用户决定是否允许为空? 或者,我认为这是一个不便,而不是一个功能?
从另一个角度来看它:如果你可以让你的函数返回平台类型LocalDate!
的值LocalDate!
,Java不安全性可能会扩展到Kotlin代码中的函数用法:它们会在任何时候返回null
,这对调用者来说可能是意外的,使用返回值非空。
反过来,Kotlin 是无效的 ,它不允许将null
静静地传递到某个会导致NPE的地方。 相反,每个值都可以为空或传递非空的检查或断言。
平台类型在语言中是不可指定的,这只是一种处理不安全的Java可空性的方法(简单地把所有的Java值视为可为空都不行 )。 他们为您提供了一种方式来表明您相信对Java代码的这种调用不会返回null :当您对待T!
作为T
,产生一个断言来检查它。 否则,你使用平台类型T!
如可空T?
。
空值安全是Kotlin语言设计的关键之一,它使您可以决定Kotlin代码中的每个值是否为空。
您有两个API设计选项:
- 返回一个非空值,检查函数内部的可空性
- 返回可为空的值,从而警告调用者可能的
null
但是,如果一个函数具有允许调用者假设它在某些条件下不会返回null
语义,那么可以创建一个包装函数来进行断言。 这是可行的,如果再加上逻辑或回退,否则它几乎不会比呼叫站点断言( !!
)更简洁。