【问题标题】:Kotlin- Extension functions and platform types?Kotlin- 扩展功能和平台类型?
【发布时间】:2016-04-01 07:43:51
【问题描述】:

我想向ResultSet 添加两个扩展函数,它们的值是LocalDate

fun ResultSet.getLocalDate(colName: String) = getDate(colName)?.toLocalDate()
fun ResultSet.getLocalDate(colIndex: Int) = getDate(colIndex)?.toLocalDate()

问题是getDate() 返回一个Date!,显然如果在toLocalDate() 之前没有?. 调用,我会得到一个空错误。但是任何使用此扩展程序的人都必须将结果用作LocalDate? 而不是LocalDate!

为了保持一致性,我有什么方法可以维护平台类型?并让扩展函数的用户决定是否允许为空?还是我错误地将其视为不便而不是功能?

【问题讨论】:

  • 我想这引出了一个更大的设计问题:如果 JDBC 是用 Kotlin 编写的,那么 every 字段 getter 是否可以为空?这可能是有道理的,因为库不知道表中的列是否可以为空......

标签: nullable kotlin kotlin-extension


【解决方案1】:

换个角度看:如果你可以让你的函数返回一个平台类型的值LocalDate!,Java 不安全的可空性将蔓延到你的 Kotlin 代码中的函数用法:它们会在任何时候返回 null ,对于使用非空返回值的调用者来说可能是意外的。

Kotlin 反过来又是 is null-safe,它不允许将 null 静默传递到会导致 NPE 的地方。相反,每个值要么作为可空传递,要么通过非空检查或断言。

Platform types 在语言中是不可表示的,这只是处理不安全的 Java 可空性的一种方法(简单地将所有 Java 值视为可空的wouldn't work)。它们为您提供了一种方式来声明您相信对 Java 代码的调用不会返回 null:当您将 T! 视为 T 时,会生成一个断言来检查它。否则,您将使用平台类型 T! 与可为空的 T? 一样。

空值安全是 Kotlin 语言设计的关键点之一,它让您决定 Kotlin 代码中的每个值是否可以为空。

API 设计有两种选择:

  • 返回一个非空值,检查函数内部的可空性
  • 返回可为空的值,从而警告调用者可能的null

但是,如果一个函数的语义允许调用者假设它在某些情况下不会返回null,那么您可以创建一个包装函数来进行断言。如果加上额外的逻辑或回退,这是可行的,否则它几乎不会比调用现场的断言 (!!) 更简洁。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2023-03-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多