也许我错过了一些明显的东西......在我看来,Kotlin在各种文档中都有各种各样的序列,它们不能互操作。即使复制序列可能效率低下 - 当我需要将它作为语义相同但不同的类型传递给函数时,这也无济于事。所以我使用这些构造函数和转换器(仅适用于Int和单向):
fun IntArray(a: Array<Int>) = IntArray( a.size ) { a[it] }
fun IntArray(c: Collection<Int>) = IntArray( c.size ) { c.elementAt(it) }
fun IntArray(p: IntProgression) = IntArray( p.toList() )
fun IntArray(s: Sequence<Int>) = IntArray( s.toList() )
fun Array<Int>.toIntArray() = IntArray( this )
fun Collection<Int>.toIntArray() = IntArray( this )
fun IntProgression.toIntArray() = IntArray( this )
fun Sequence<Int>.toIntArray() = IntArray( this )
/* If constructors are not desirable:
fun Array<Int>.toIntArray() = IntArray( size ) { get(it) }
fun Collection<Int>.toIntArray() = IntArray( size ) { elementAt(it) }
fun IntProgression.toIntArray() = toList().toIntArray()
fun Sequence<Int>.toIntArray() = toList().toIntArray()*/
有没有理由不在标准库中拥有所有这些变体,也许是内联的?第三个甚至允许一个很好的初始化语法:
val ia = IntArray( 7 .. 11 )
答案 0 :(得分:4)
实际上,stdlib中有一些功能可以进行转换:请参阅.toIntArray()
,它与Array<out Int>
和Collection<Int>
一起使用。其他原始类型也有这样的转换:.toLongArray()
,.toByteArray()
等。
但是,IntProgression
和Sequence<Int>
没有此类扩展名,您必须自行实施或使用中间数组或集合。
这种缺席的原因可能是你不鼓励你在你的代码中使用数组,除了性能关键部分,而不是使用列表和其他集合的惯用语。
此外,三种Kotlin容器Collection<T>
,Sequence<T>
和Array<T>
可以相互转换,请参阅:
.asSequence()
.toTypedArray()
(似乎缺少Sequence<T>
).toCollection()
(以及Sequence<T>
:.toCollection()
)答案 1 :(得分:2)
Array<Int>
和IntArray
无法互操作,因为它们的类型非常不同。第一个映射到Integer[]
,第二个映射到int[]
。原始int[]
将更加高效,因为它是连续存储的,而第一个基本上分配一个对象数组,其中每个槽指向Integer
对象。使用int[]
,内存使用和性能都会非常优越。
Kotlin喜欢明确这些类型的事情,正如您所指出的那样,在需要时编写自己的转换需要一行。
PS:看起来Kotlin确实有从Collection
数字到原始数组的扩展函数:
public fun Collection<Int>.toIntArray(): IntArray {
val result = IntArray(size)
var index = 0
for (element in this)
result[index++] = element
return result
}