5

我有一个看起来像这样的函数:

fun MyInput?.toOutput() : Output? {
  if (this == null) return null
  return Output(this.someValue)
}

在我知道 myMyInput不为空的地方(例如,在将 ainput: MyInput作为参数的方法中),我希望能够使用input.toOutputasOutput而不是Output?

我试过使用

contract {
  returnsNotNull() implies (this@toOutput != null)
}

但这意味着倒退。这告诉我,如果toOutput返回非空类型,则 myinput是非空的。我想根据参数告诉分析器有关返回值的信息。在 Java 中,我可以使用org.jetbrains.annotations.@Contract("null -> null ; !null -> !null")它来完成此操作。

有没有办法在 Kotlin 中做到这一点?

4

1 回答 1

8

您不需要为此签订合同。你只需要做一个不可为空的重载。像这样:

fun MyInput?.toOutput(): Output? {
  if (this == null) return null
  return Output(this.someValue)
}

fun MyInput.toOutput(): Output = Output(this.someValue)

但是,这在 JVM 上不会开箱即用,因为函数签名会发生冲突。要使其工作,您必须为其中一个函数指定一个带有@JvmName注释的新名称。例如:

@JvmName("toOutputNonNull")
fun MyInput.toOutput(): Output = Output(this.someValue)

您仍然可以像从 Kotlin 中那样调用它,但是如果您从 Java 中调用它input.toOutput(),它就会变成类似的东西。FileNameKt.toOutputNonNull(input)

于 2019-04-25T16:34:50.280 回答