If I have to generate two groups based on two different fields using Stream, this is one approach I can take:
var prop1Group = beans.stream().collect(Collectors.groupingBy(Bean::getProp1));
var prop2Group = beans.stream().collect(Collectors.groupingBy(Bean::getProp2));
But this approach iterates over the list twice. In an imperative way, I can get the same result in single iteration, like this:
var prop1Group = new HashMap<String, Set<Bean>>();
var prop2Group = new HashMap<String, Set<Bean>>();
for (var bean : beans) {
prop1Group.computeIfAbsent(bean.getProp1(), key -> new HashSet<>()).add(bean);
prop2Group.computeIfAbsent(bean.getProp2(), key -> new HashSet<>()).add(bean);
}
Is there anyway to do get the same done in declarative way using streams, without iterating twice?
As per the comment from @Holger, I could write it more declaratively with teeing, like this, but this still costs 2N
beans.stream().collect(
Collectors.teeing(
groupingBy(Bean::getProp1),
groupingBy(Bean::getProp2),
List::of))
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With