I have a stream, where each object is identified by a unique id.
Moreover, each object has a either positive or negative Free
values.
I want to divide this stream into two Sets, where one contains the ids
whose Free
values was positive, and one with the rest.
But I find the following not being the right way, as I’m collecting into lists outside of the stream.
class Foo { int free; long id; } public Tuple2<Set<Long>, Set<Long>> findPositiveAndNegativeIds() { Set<Long> positives = new HashSet<>(); Set<Long> negatives = new HashSet<>(); foos.stream() .forEach(f -> { if (f.free >= 0) positigves.add(f.id); else negatives.add(f.id); }); return Tuple2.tuple(positives, negatives); }
Could this be done better, somehow with partitionBy()
or similar?
Advertisement
Answer
You can indeed use partitioningBy
. You can specify what to do with each partition in the second parameter.
var map = foos.stream().collect(Collectors.partitioningBy( foo -> foo.free >= 0, // assuming no 0 // for each partition, map to id and collect to set Collectors.mapping(foo -> foo.id, Collectors.toSet()) ));
map.get(true)
will get you the set of id
s with positive free
s, and map.get(false)
will get you the set of ids
with negative free
s.