Anshul Lonkar
Anshul Lonkar

Reputation: 83

How to convert this code to JAVA 8 Stream API?

I want to convert this while loop to equivalent code using a Java 8 Streams, but I don't know how to both stream the List and remove elements from it.

private List<String> nameList = new ArrayList<>();

while (nameList.size() > 0) {
    String nameListFirstEntry = nameList.get(0);
    nameList.remove(0);
    setNameCombinations(nameListFirstEntry);
}

Upvotes: 2

Views: 879

Answers (2)

Bohemian
Bohemian

Reputation: 425033

Because List#remove(int) also returns the element, you can both stream the list's elements and remove them via a stream:

Stream.generate(() -> nameList.remove(0))
    .limit(nameList.size())
    .forEach(this::setNameCombinations);

This code doesn't break any "rules". From the javadoc of Stream#generate():

Returns an infinite sequential unordered stream where each element is generated by the provided Supplier. This is suitable for generating constant streams, streams of random elements, etc.

There is no mention of any restrictions on how the supplier is implemented or that is must have no side effects etc. The Supplier's only contract is to supply.


For those who doubt this is "works", here's some test code using 100K elements showing that indeed order is preserved:

int size = 100000;
List<Integer> list0 = new ArrayList<>(size); // the reference list
IntStream.range(0, size).boxed().forEach(list0::add);
List<Integer> list1 = new ArrayList<>(list0); // will feed stream
List<Integer> list2 = new ArrayList<>(size);  // will consume stream

Stream.generate(() -> list1.remove(0))
        .limit(list1.size())
        .forEach(list2::add);

System.out.println(list0.equals(list2)); // always true

Upvotes: 4

Gerald M&#252;cke
Gerald M&#252;cke

Reputation: 11132

I guess this will do

nameList.forEach(this::setNameCombinations);
nameList.clear();

In case you don't need the original list anymore, you might as well create a new empty list instead.

Upvotes: 6

Related Questions