guava/src/com/google/common/collect/Multimaps.java
@Beta
  public static <T, K, V, M extends Multimap<K, V>> Collector<T, ?, M> toMultimap(
      java.util.function.Function<? super T, ? extends K> keyFunction,
      java.util.function.Function<? super T, ? extends V> valueFunction,
      java.util.function.Supplier<M> multimapSupplier) {
    checkNotNull(keyFunction);
    checkNotNull(valueFunction);
    checkNotNull(multimapSupplier);
    return Collector.of(
        multimapSupplier,
        (multimap, input) -> multimap.put(keyFunction.apply(input), valueFunction.apply(input)),
        (multimap1, multimap2) -> {
          multimap1.putAll(multimap2);
          return multimap1;
        });
  }
@Beta
  public static <T, K, V, M extends Multimap<K, V>> Collector<T, ?, M> toMultimap(
      java.util.function.Function<? super T, ? extends K> keyFunction,
      java.util.function.Function<? super T, ? extends V> valueFunction,
      java.util.function.Supplier<M> multimapSupplier) {
    checkNotNull(keyFunction);
    checkNotNull(valueFunction);
    checkNotNull(multimapSupplier);
    return Collector.of(
        multimapSupplier,
        (multimap, input) -> multimap.put(keyFunction.apply(input), valueFunction.apply(input)),
        (multimap1, multimap2) -> {
          multimap1.putAll(multimap2);
          return multimap1;
        });
  }
Returns a {@code Collector} accumulating entries into a {@code Multimap} generated from the
specified supplier. The keys and values of the entries are the result of applying the provided
mapping functions to the input elements, accumulated in the encounter order of the stream.

<p>Example:

<pre>{@code
static final ListMultimap<Character, String> FIRST_LETTER_MULTIMAP =
Stream.of("banana", "apple", "carrot", "asparagus", "cherry")
.collect(
toMultimap(
str -> str.charAt(0),
str -> str.substring(1),
MultimapBuilder.treeKeys().arrayListValues()::build));

// is equivalent to

static final ListMultimap<Character, String> FIRST_LETTER_MULTIMAP;

static {
FIRST_LETTER_MULTIMAP = MultimapBuilder.treeKeys().arrayListValues().build();
FIRST_LETTER_MULTIMAP.put('b', "anana");
FIRST_LETTER_MULTIMAP.put('a', "pple");
FIRST_LETTER_MULTIMAP.put('a', "sparagus");
FIRST_LETTER_MULTIMAP.put('c', "arrot");
FIRST_LETTER_MULTIMAP.put('c', "herry");
}
}</pre>

@since 21.0