Java 8 stream.collect (… groupingBy (… mapping (… redução))) reduzindo o uso de BinaryOperator

Eu brinquei com uma solução usandogroupingBy, mapping ereducing para a seguinte pergunta:Crie de forma elegante o mapa com campos de objetos como chave / valor do fluxo de objetos em Java 8. Resumiu o objetivo era obter um mapa com a idade como chave e os hobbies de uma pessoa comoSet.

Uma das soluções que eu encontrei (não é legal, mas não é esse o ponto) teve um comportamento estranho.

Com a seguinte lista como entrada:

List<Person> personList = Arrays.asList(
     new Person(/* name */ "A", /* age */ 23, /* hobbies */ asList("a")),
     new Person("BC", 24, asList("b", "c")),
     new Person("D", 23, asList("d")),
     new Person("E", 23, asList("e"))
);

e a seguinte solução:

Collector<List<String>, ?, Set<String>> listToSetReducer = Collectors.reducing(new HashSet<>(), HashSet::new, (strings, strings2) -> {
  strings.addAll(strings2);
  return strings;
});
Map<Integer, Set<String>> map = personList.stream()
                                          .collect(Collectors.groupingBy(o -> o.age, 
                                                                         Collectors.mapping(o -> o.hobbies, listToSetReducer)));
System.out.println("map = " + map);

Eu tenho:

map = {23=[a, b, c, d, e], 24=[a, b, c, d, e]}

claramente não era o que eu estava esperando. Eu esperava isso:

map = {23=[a, d, e], 24=[b, c]}

Agora, se eu apenas substituir a ordem de(strings, strings2) do operador binário (do coletor redutor) para(strings2, strings) Eu recebo o resultado esperado. Então, o que eu perdi aqui? Eu interpretei mal oreducing-colecionador? Ou qual a documentação que perdi que torna óbvio que meu uso não estava funcionando conforme o esperado?

A versão Java é 1.8.0_121, se isso importa.

questionAnswers(1)

yourAnswerToTheQuestion