Jeeppp
Jeeppp

Reputation: 1573

Java stream batch process of list

I've a list and I wanted to take every '25' items from the list and send it to a method that returns a map.

The batches method below would give me a list stream of 25 items and its working fine

The code throws a incompatible types when I try to assign it to a map

This is what I wrote

public class Processor{
@Inject
private Delivery delivery;

public String process(List<String> item) throws Exception{

Map<String,List<String>> tempMap = batches(item,25).forEach(i -> delivery.process(i));
//the method delivery.process would take a list and returns a map(string,list)
}
public static  Stream<List<String>> batches(List<String> source, int length) {
    if (length <= 0)
        throw new IllegalArgumentException("length = " + length);
    int size = source.size();
    if (size <= 0)
        return Stream.empty();
    int fullChunks = (size - 1) / length;
    return IntStream.range(0, fullChunks + 1).mapToObj(
            n -> source.subList(n * length, n == fullChunks ? size : (n + 1) * length));
}


}

Upvotes: 1

Views: 847

Answers (2)

Ebraheem Alrabeea
Ebraheem Alrabeea

Reputation: 2250

forEach doesn't return a Map it is a void return type method, Also even if it return a Map, the tempMap will be overridden each time, So you have to do something else instead of forEach, or do it like this:

    Map<String, List<String>> tempMap = new HashMap<>();
    batches(item, 25).forEach(i -> {
        tempMap.putAll(delivery.process(i));
    }); 

Upvotes: 1

Ousmane D.
Ousmane D.

Reputation: 56393

as mentioned by others already, the reason why your code is not working is due to the fact that forEach is a terminal operation which returns void.

as for preventing the problem, I'd go with something as such:

Map<String, List<String>> result = 
                        batches(item, 25)
                        .map(delivery::process)
                        .collect(HashMap::new, Map::putAll, Map::putAll);

Upvotes: 0

Related Questions