Does Kotlin’s version of Java’s for each have the same limitations?

Tags: , ,



I’m currently learning Kotlin coming from Java. In Java, doing

for(String s:stringList){
   if(condition == true) stringList.remove(s);
}

doesn’t work, as you can only read data with for each. Does this also apply to Kotlin?

Answer

It’s the same restriction as in Java – when you’re iterating over a collection, you’re limited to modifying it through the Iterator‘s remove() method

Removes from the underlying collection the last element returned by this iterator (optional operation). This method can be called only once per call to next(). The behavior of an iterator is unspecified if the underlying collection is modified while the iteration is in progress in any way other than by calling this method.

Kotlin has its own equivalent (bearing in mind Kotlin uses the concept of mutable and immutable lists, so you can only do this with a MutableList)

The problem with the foreach / enhanced for structure is it doesn’t expose the Iterator you need to call remove() on, and you’re not allowed to call remove() on the collection itself. And Kotlin’s the same – so your options are basically

  • use for/forEach (but you can’t modify the collection)
  • call the collection’s iterator() method and iterate over it yourself (now you can call remove() on it, with the restrictions I quoted)
  • avoid mutability and produce a new collection

The last one is what you’re encouraged to do in Kotlin – instead of modifying a collection, try to use immutable ones and transform them into new collections instead:

stringList.filterNot { condition }

If you get familiar with all the collection functions (yeah, there are a lot of them) you’ll get an idea of the ways you can transform A to B, and the convenience functions that are there to help you do it (e.g. filterTo which lets you provide a MutableList to populate with the items you want to keep).

If you do want to modify mutable collections in place though, it’s possible but you have to manage it yourself, because it’s inherently dangerous and the system can’t guarantee you’re doing it safely.



Source: stackoverflow