简体   繁体   中英

How to create list of object instead of map with groupingBy collector?

I have following stream operation.

Map<String, Integer> pieDataMap = expenses.stream()
    .collect(groupingBy(expense -> typeClassifier.apply(expense, chartCriteria), 
                        summingInt(Expense::getCost)));

Instead of getting Map<String, Integer> , I want to get list of objects of type PieEntry class which has two arg constructor PieEntry(String, Integer) . In short, I want to convert each entry (of type <String, Integer>) of map to object of PieEntry class (with two argument constructor) and collect resultant objects as list.

How can I do that without iterating over the resulting map and creating objects in an extra loop?

If the question is whether it can be done using the original stream without grouping to a map, then it's not possible. To group the results, the whole input needs to be processed since there is no way to know whether there will be new elements downstream that will end up in one of the groups.

So you have to get a grouping map and then map its entries to PieEntry objects:

pieDataMap.stream().entrySet().stream().map(entry -> new PieEntry(entry.getKey(), entry.getValue()));

You can also chain it to the original stream chain after .collect() .

According to groupingBy function signature,

static <T,K,A,D> Collector<T,?,Map<K,D>>    groupingBy(Function<? super T,? extends K> classifier, Collector<? super T,A,D> downstream)

it returns a collector which produces (collects elements into) a map & as this operation is terminal operation, resulting map can't be processed any more in same statement.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM