Kotlin optimize take first n elements with filter

Viewed 1128

I have some list: List <Pet> I need to take 3 elements from it that satisfy the condition:

I do it like this:

list.filter { g -> !mainList.contains(g) }.take(3)

How can you optimize this code so that the filter operation is executed no more than enough times for the result?

1 Answers

Use a sequence. Instead of fully processing each step in turn (i.e. create a new filtered list, then take 3 elements from that) each element passes through the chain, one at a time. So you don't create intermediate lists, and you can stop as soon as you get to the element that meets your terminating condition

list.asSequence()
    .filter { g -> !mainList.contains(g) }
    .take(3)
    .toList()

Note you have to execute the sequence (with toList in this case) to turn it into a concrete collection.

Also, as the link says, creating a sequence does introduce a bunch of overhead, so it's not necessarily more efficient - you'll see benefits with bigger collections, more steps in the chain, slower computation in things like the filter functions... anything where it makes sense to really minimise memory use or exiting early makes a big difference. You should benchmark it, make sure it's the right thing to do!

Also as a bonus, your filter operation could be filterNot(mainList::contains) if you like!

Related