如何创建一个在Kotlin中填充空值的通用数组?

我试过这个,代码没有编译。

class GenericClass() { private var arr : Array? = null { arr = Array(10, { null }) } } 

这个代码中报告了两个编译器错误:一个是可空types,另一个是generics​​。

可空types 。 Kotlin强制使用可空引用的规则,并且由于T可以用例如使arr为Arraytypes的String实例化,因此编译器不允许将空值放入此数组中。 如果你想要null,你必须改变types为Array:

 class GenericClass() { private var arr : Array? = null { arr = Array(10, { null }) // No need to specify type arguments again } } 

generics 。 上面的例子仍然有一个编译时错误,因为我们试图构造一个未知types的数组T. 注意这个问题也存在于Java中。 被编译为JVM字节码的Kotlin需要两件事情:

  • genericstypes参数在运行时被擦除,
  • 除了数组的通用参数。

这意味着在字节码中Kotlin必须创建一个具体types的数组,而不是一个未知的typesT.它可以创建对象的数组,每当它看到数组,但是这不起作用,例如在这种情况下:

 fun test() { fun foo(srts: Array) { // ... } val gc = GenericClass() foo(gc.arr) } 

在这里,在最后一行,我们正在尝试传递Object [],其中String []是期望的,并且得到一个运行时错误。

这就是为什么Kotlin拒绝创建T的数组。你可以通过明确地禁止types系统,即通过使用types转换来解决这个问题:

 class GenericClass() { val arr : Array { arr = Array(10, { null }) as Array } } 

这里我们明确地要求创建一个Any(编译成Object [])的数组,然后将其转换为T的数组。编译器发出警告,但是服从我们的意愿。

请注意,上面有问题的例子仍然存在,也就是说,如果您希望传递以这种方式创建的数组的字符串,那么在运行时就会失败。

方法

 val array : Array = kotlin.arrayOfNulls(size) 

从文档

 /** *Returns an array of objects of the given type with the given [size], *initialized with null values. */ public fun  arrayOfNulls(size: Int): Array