This is a contrived example for the sake of my understanding Kotlin language.
The class Box<T> below models a box that contains boxes of the same type T.
The question is why arr += x causes compile error while arr.add(x) does not.
The error message is:
Type mismatch. Required: kotlin.collections.ArrayList<Box>
Found: List<Box>
the property arr is immutable and points to a mutable list. So I believe there is no ambiguity whether arr += x should mean arr = arr + x or arr.add(x). It should mean arr.add(x)
I also noticed that the issue is gone if generic type Box implements Iterable<T> instead of Iterable<Box<T>>
So, what is the reason of the error?
class Box<T>(private val arr: ArrayList<Box<T>> = ArrayList()) : Iterable<Box<T>> {
private val id: Int = seq++
override operator fun iterator(): Iterator<Box<T>> {
return object : Iterator<Box<T>> {
private var i = 0;
override fun hasNext(): Boolean {
return i < arr.size
}
override fun next(): Box<T> {
return arr[i++]
}
}
}
fun add(x: Box<T>) {
// arr.add(x) // OK
arr += x // Error: Type mismatch.
}
companion object {
var seq: Int = 0
}
override fun toString(): String {
return "Box[$id]"
}
}
fun main() {
val box = Box<Int>(arrayListOf(Box(), Box()))
for (x in box) {
println(x)
}
}