Question

I'm playing around with Java 8 and I know that this must be possible by reading the documentation, I just cannot find out how to do it.

I have the following working code:

    long factorProduct = LongStream.rangeClosed(1, maxFactor)
            .filter(this::isOptimalFactor)
            .reduce((i, j) -> i * j)
            .getAsLong();
    List<Long> primeFactors = primeFactors(factorProduct);

Important part is that I have a List<Long> that may have duplicates on some Long numbers.

Now I want to convert it to a Map<Long, Long> with as key the element and as value the occurences.

I thought that:

    Map<Long, Long> primeFactorCount = primeFactors.stream()
            .collect(Collectors.counting());

would work, but it doesn't. I looked up the examples in the java.util.stream.Collectors documentation.

How do I need to use these features?

Was it helpful?

Solution

If you want to group the elements, you have to use groupingBy:

import static java.util.stream.Collectors.*;

Map<Long, Long> primeFactorCount = primeFactors.stream()
        .collect(groupingBy(p -> p, counting()));

OTHER TIPS

If you use Eclipse Collections, you could use the following for the prime factors list and the prime factor count. A Bag is basically a Map<K, Integer>.

MutableList<Long> primeFactors = this.primeFactors(factorProduct); 
Bag<Long> primeFactorCount = primeFactors.toBag();

Use a FastList in the primeFactors method above.

In the case of Eclipse Collections we have primitive Lists and Bags, so you will not need to box any results.

LongList primeFactors = this.primeFactors(factorProduct);   
LongBag primeFactorCount = primeFactors.toBag();

Use a LongArrayList instead in the primeFactors method above.

Note: I am committer for Eclipse Collections.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top