如何在Kotlin中为函数类型变量赋值空值?

x2b*_*ool 35 function-pointers function kotlin

我有一个包含回调的变量,默认情况下它的值应为null.但是这种语法似乎不起作用.

var callback1 : () -> Unit = null
var callback2 : ((a) -> c, b) -> Unit = null
Run Code Online (Sandbox Code Playgroud)

我目前的解决方案是确保回调具有默认实现.

var callback1 : () -> Unit = { }
var callback2 : ((a) -> c, b) -> Unit = { a, b -> }
Run Code Online (Sandbox Code Playgroud)

但是,这使得很难检查回调是否已设置,并且可能默认实现是否需要付出一定的代价(是这样吗?).如何在Kotlin中为函数类型变量赋值空值?

Sea*_*lly 53

与Kotlin中的所有变量一样,函数引用通常不能为null.为了允许空值,您必须?在类型定义的末尾添加一个,如下所示:

var callback1 : (() -> Unit)? = null
var callback2 : (((a) -> c, b) -> Unit)? = null
Run Code Online (Sandbox Code Playgroud)

您通常需要围绕整个函数类型声明的括号.即使它不是必需的,也可能是个好主意.您还需要使用invokenull-safe运算符来调用函数:

callback1?.invoke()
Run Code Online (Sandbox Code Playgroud)

从长远来看,无所事事的实现方法可能更方便,对我来说似乎更"kotlin-y".与计算机科学中的大多数事情一样,我不担心默认实现的性能成本,除非您有特定的性能数据表明它是一个问题.

确定是否在不允许空值的情况下设置回调的一种方法是使用空对象模式:

val UNSET_CALLBACK1: () -> Unit = {}
var callback1 : () -> Unit = UNSET_CALLBACK1
fun callback1IsSet(): Boolean {
    return callback1 !== UNSET_CALLBACK1
}
Run Code Online (Sandbox Code Playgroud)

希望这可以帮助!

  • 这是很合理的。blah..invoke()的意思是“如果不为空则调用blah”,如果blah可以为null,则很有必要。解决方案就是做到这一点。我将更新答案以澄清这一点。 (2认同)