3

Let's say I have a list of Brand objects. The POJO contains a getName() that returns a string. I want to build a Map<String, Brand> out of this with the String being the name... but I want the key to be case insensitive.

How do I make this work using Java streams? Trying:

brands.stream().collect(Collectors.groupingBy(brand -> brand.getName().toLowerCase()));

doesn't work, which I think is because I'm not using groupBy correctly.

Naman
  • 27,789
  • 26
  • 218
  • 353
IcedDante
  • 6,145
  • 12
  • 57
  • 100
  • No- right off the bat I realize I shouldn't be using groupingBy because that returns a List. Let me clarify the return type a little more... there! so the problem is it doesn't compile because it tries to return an Object key – IcedDante Oct 01 '15 at 15:39

1 Answers1

9

Collect the results into a case insensitive map

Map<String, Brand> map = brands
     .stream()
     .collect(
          Collectors.toMap(
              Brand::getName, // the key
              Function.identity(), // the value
              (first, second) -> first, // how to handle duplicates
              () -> new TreeMap<String, Brand>(String.CASE_INSENSITIVE_ORDER))); // supply the map implementation

Collectors#groupBy won't work here because it returns a Map<KeyType, List<ValueType>>, but you don't want a List as a value, you just want a Brand, from what I've understood.

Community
  • 1
  • 1
Sotirios Delimanolis
  • 274,122
  • 60
  • 696
  • 724
  • Thanks Sotirios. I feel like I shouldn't use this implementation yet because no one on my team would understand it. Hah! I'm sure that will change with time but the solution definitely works. – IcedDante Oct 01 '15 at 15:44
  • BTW: can you explain why groupingBy doesn't work for my situation? – IcedDante Oct 02 '15 at 13:54
  • @IcedDante From your question, you seem to want a `Map`. `groupBy` would have returned a `Map>`. That's what it does, it groups (`List`) values by some property. – Sotirios Delimanolis Oct 02 '15 at 16:49