Is `MutableCollection.addAll(Collection/Iterable/S...
# stdlib
s
Is
MutableCollection.addAll(Collection/Iterable/Sequence/Array
) faster if the input and/or output are certain types of collections?
e
there isn't an
Iterable.addAll
method; do you mean
MutableCollection.addAll
?
https://github.com/JetBrains/kotlin/blob/master/libraries/stdlib/src/kotlin/collections/MutableCollections.kt#L114
Copy code
fun <T> MutableCollection<in T>.addAll(elements: Iterable<T>): Boolean
is an extension function which forwards to the
Copy code
interface MutableCollection<E> {
    fun addAll(elements: Collection<E>): Boolean
}
member if
elements is Collection
else it adds the elements one-by-one. whether the member function
.addAll
does anything better depends on the receiver in question
java.util.ArrayList
, which is what you'll get if you use
mutableListOf()
in Kotlin (in current implementation, not guaranteed by the API contract), does pre-allocate space so it can grow the backing array only once, but this has the same big-O amortized runtime
s
There's no special magic that some collections can be added in constant time or something? Maybe some compiler optimizations I can't see from the source?
e
the only way you could get O(1) is if the elements to be added are an immutable collection, which isn't a standard type that anything knows about
s
Meaning there are no immutable collections in Kotlin? Aren't there in Java?
e
there are some libraries such as https://github.com/Kotlin/kotlinx.collections.immutable but not in stdlib. no, although Java does now have builders for immutable collections (like Kotlin), it doesn't have types for them
e.g.
listOf()
and java.util.List.of() are immutable, but you don't know it from the type
s
So
mutableListOf().addAll(listOf())
runs in linear time (no more efficient than
Iterable
), and adding an immutable list would theoretically be O(1), but there aren't any such types...?
e
adding an immutable list, if the receiver knew how to handle it and was structured in a particular way, could potentially be O(1), but in general can't be for an array-backed list
s
So it is all just linear? No point in converting an array to a list for addAll?
e
can't do better than linear if you have to copy O(n) elements
s
Can you do worse? Are there such worse implementations?
e
internally, ArrayList.addAll() does convert to an array first, so it can pre-allocate without worrying about inconsistencies between count() and iterator() of a mutable collection
yes, of course you can do worse