3

I was trying to write a solution for the problem stated here as Stuart Marks pointed out to use a helper class. I got stuck on the code due to this error:

Test.java:27: error: incompatible types: inference variable K has incompatible bounds                                                                                                                          
         .collect(Collectors.groupingBy(p -> p.getT2()));                                                                                                                                                      
                 ^                                                                                                                                                                                             
    equality constraints: Tuple                                                                                                                                                                                
    lower bounds: Integer                                                                                                                                                                                      
  where K,T are type-variables:                                                                                                                                                                                
    K extends Object declared in method <T,K>groupingBy(Function<? super T,? extends K>)                                                                                                                       
    T extends Object declared in method <T,K>groupingBy(Function<? super T,? extends K>) 

My current code:

import java.util.stream.IntStream;
import java.util.stream.Collectors;
import java.util.Map;

public class Test{

    private static final class Tuple {
        private final Integer t1;
        private final Integer t2;

        private Tuple(final Integer t1, final Integer t2) {
            this.t1 = t1;
            this.t2 = t2;
        }

        public Integer getT1() { return t1; }
        public Integer getT2() { return t2; }
    }

     public static void main(String []args){
        System.out.println("Hello World");

        Map<Tuple, Integer> results =
        IntStream.range(1, 10).boxed()
         .map(p -> new Tuple(p, p % 2))                     // Expensive computation
         .filter(p -> p.getT2() != 0)
         .collect(Collectors.groupingBy(p -> p.getT2())); 

        results.forEach((k, v) -> System.out.println(k + "=" + v));
     }

}

I'm quite new to Java 8 myself, the solution might be wrong but I have no clue what the error means or how to resolve it. The Tuple class used to be generic as well but since I thought that caused the problem I removed the generic types but the same error remained.

Community
  • 1
  • 1
Juru
  • 1,623
  • 17
  • 43
  • 2
    See also http://stackoverflow.com/questions/29946938/java-streams-groupingby-same-elements/29947129#29947129 (the second part) – Alexis C. May 19 '15 at 22:41

1 Answers1

4

collect() and groupingBy() do not do what you think they do. The result type of your assignment as it is right now is:

Map<Integer, List<Tuple>> results = ...

In other words, you're grouping by p.getT2() (Integer) and in each group, collect the tuples of that group into a List<Tuple>, resulting in something like:

1=[Test$Tuple@7699a589, Test$Tuple@58372a00, Test$Tuple@4dd8dc3, 
   Test$Tuple@6d03e736, Test$Tuple@568db2f2]
Lukas Eder
  • 211,314
  • 129
  • 689
  • 1,509
  • Thanks! Stupid of me. I guess I was too eager to find a solution for the problem and not reading the api well enough :-). – Juru May 19 '15 at 23:04
  • 1
    @Juru: Well, the API is hard to read... But if you're using an IDE, you can let it auto-complete the assigned type for you - that may help :) – Lukas Eder May 20 '15 at 07:39
  • Yeah good idea, I was writing it on an online compiler :-). No auto-completion there. – Juru May 20 '15 at 07:50