This week's book giveaway is in the Beginning Java forum.
We're giving away four copies of Murach's Java Programming and have Joel Murach on-line!
See this thread for details.
Win a copy of Murach's Java Programming this week in the Beginning Java forum!
  • Post Reply Bookmark Topic Watch Topic
  • New Topic

Need Help with Comparator question in Stream  RSS feed

 
Thomas Roth
Greenhorn
Posts: 10
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Hi folks,

i need help with following situation:

List<String> list = Arrays.asList(
                "Bob", "Sarah", "Marcus","Leander","Thomas");


I just can not understand why this works:



while this does NOT work:




I know it must have something to do with the method references, but i just cant figure it out.

Similar problem, why does this then work:


but if i write for com1 the "Comparator.comparing(s->s.length())" in the sorted() it again wont work. ?

Any help would be appreciated
 
Stephan van Hulst
Saloon Keeper
Posts: 7476
134
  • Likes 2
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
The way Java performs type inference on lambda expressions is very complex and will take a long time to explain. The short answer is that in the first case, you explicitly told the compiler to use the length() method of the String class, while in the second case, the compiler has to infer that you want to use the String class. Part of the reason why the compiler is not able to infer that you want to use String, is because comparing() takes a generic type with a parameter that has a lower bound. So when you write Comparator.comparing(s -> s.length()), the compiler interprets that as Comparator.comparing((Object s) -> s.length()). As you know, Object doesn't have a length() method. The compiler does not look at the surrounding method call to provide the comparing() method with more context.

You can fix this by explicitly stating the type of the lambda argument, or by passing the generic type arguments to the comparing() method explicitly:
 
Thomas Roth
Greenhorn
Posts: 10
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Stephan van Hulst wrote:The way Java performs type inference on lambda expressions is very complex and will take a long time to explain. The short answer is that in the first case, you explicitly told the compiler to use the length() method of the String class, while in the second case, the compiler has to infer that you want to use the String class. Part of the reason why the compiler is not able to infer that you want to use String, is because comparing() takes a generic type with a parameter that has a lower bound. So when you write Comparator.comparing(s -> s.length()), the compiler interprets that as Comparator.comparing((Object s) -> s.length()). As you know, Object doesn't have a length() method. The compiler does not look at the surrounding method call to provide the comparing() method with more context.

You can fix this by explicitly stating the type of the lambda argument, or by passing the generic type arguments to the comparing() method explicitly:


Thank you very much Stephan, that was a very good explanation and helped me to understand what is going on there. ;)
 
  • Post Reply Bookmark Topic Watch Topic
  • New Topic
Boost this thread!