null to listOf(),not null to listOf(value)in Kotlin in one liner?
让f()
返回一个可为空的值。
我想要做的是这个
如果f()
为null,则获取一个空列表,
否则,如果f()
不为null,则获取单个项目value
的列表。
在斯卡拉,我们可以做这样的事情:
Option(f()).toList
或更详细地说
Option(f()).map(v => List(v)).getOrElse(List.empty)
在Kotlin中,没有Option
(假设没有Funktionale库),并且null在Scala中不具有toList()
不像( None: Option
)。
我们有Elvis操作符,但是null将会在listOf()
函数内部,所以会是
listOf(f() ?: /* What can I do here? */)
我们想要的null是listOf(/*no argument */)
,但是Elvis操作符需要一个参数,所以listOf(f() ?: )
将导致编译错误。
至少我们能做到
val v = f() if (v == null) listOf() else listOf(v)
但它是一个两班轮船。
有这个表达吗?
在那里我将使用这个表达式是在类的主要构造函数的默认参数,所以如果它不是一个班轮,它将被括在方括号,所以这样的事情:
class A( val p1: List<V> = run { val v = f() if (v == null) listOf() else listOf(v) }, val p2: ... = ..., ...)
这看起来很丑,不是吗?
编辑
正如@Naetmul所指出的那样, listOfNotNull(f())
在语法上比我最初在下面发表的内容要好,而且还需要可变数目的参数
val myList = listOfNotNull(f(), g(), h())
将返回非空的所有结果的列表。
我会用在这里。
val myList = f()?.let { listOf(it) } ?: emptyList()
使用?.
安全地调用 f()
的返回值,然后使用let
来运行一个代码块。 如果f()
是null,它将不会运行这个代码块,导致一个空值。 然后我们使用?:
elvis操作符回退到空列表。
在这里它被分成几行以便更好地理解
val myValue = f() val myList: List<Any> if (myValue != null) { myList = listOf(myValue) } else { myList = emptyList() }
对于这个具体的问题,我可以做
listOfNotNull(f())