ImmutableMapFactory { public static <K, L, V, W> ImmutableMap<L, W> create( Map<K, V> baseMap, BiFunction<? super K, ? super V, ? extends L> keyCreator, BiFunction<? super K, ? super V, ? extends W> valueCreator) { return baseMap.entrySet().stream() .collect(ImmutableMap.toImmutableMap( e -> keyCreator.apply(e.getKey(), e.getValue()), e -> valueCreator.apply(e.getKey(), e.getValue()))); }  static ImmutableMap<L, W> create(
            Map<K, V> baseMap,
            BiFunction<? super K, ? super V, ? extends L> keyCreator,
            BiFunction<? super K, ? super V, ? extends W> valueCreator); static ImmutableMap<L, W> create(
            Map<K, V> baseMap,
            Function<? super K, ? extends L> keyMapper,
            Function<? super V, ? extends W> valueMapper); static ImmutableMap<L, W> createAndReduceCollisions(
            Map<K, V> baseMap,
            Function<? super K, ? extends L> keyMapper,
            Function<? super V, ? extends W> valueMapper,
            W valueIdentity,
            BinaryOperator<W> collidingKeysAccumulator); static ImmutableMap<L, V> createWithNewKeys(
            Map<K, V> baseMap,
            Function<? super K, ? extends L> keyMapper); static ImmutableMap<K, W> createWithNewValues(
            Map<K, V> baseMap,
            Function<? super V, ? extends W> valueMapper); static ImmutableMap<K, W> createWithNewValues(
            Map<K, V> baseMap,
            BiFunction<? super K, ? super V, ? extends W> valueMapper); static ImmutableMap<K, V> createFromKeys(
            Collection<K> keys,
            Supplier<V> valueSupplier); static ImmutableMap<K, V> createFromKeys(
            Collection<K> keys,
            Function<K, V> valueCreator); static ImmutableMap<K, V> zip(
            List<K> keys,
            List<V> values); static ImmutableMap<K, V> filter(
            Map<K, V> baseMap,
            BiPredicate<K, V> filter); static ImmutableMap<K, V> filterByKeys(
            Map<K, V> baseMap,
            Predicate<K> keyFilter); static ImmutableMap<K, V> filterByValues(
            Map<K, V> baseMap,
            Predicate<V> valueFilter); static ImmutableMap<K, V> parse(
            String s,
            Function<String, K> keyParser,
            Function<String, V> valueParser); static ImmutableMap<K, V> parseAndFilter(
            String s,
            Function<String, K> keyParser,
            Function<String, V> valueParser,
            BiPredicate<K, V> filter);  }
@Test void testCreateWithBothKeyMapperAndValueMapper() { ImmutableMap<Integer, Integer> baseMap = ImmutableMap.of( 1, 2, 2, 3, 3, 4, 4, 5); ImmutableMap<Integer, Integer> expected = ImmutableMap.of( 1, 4, 4, 6, 9, 8, 16, 10); ImmutableMap<Integer, Integer> actual = ImmutableMapFactory.create( baseMap, key -> key * key, value -> value * 2); Assertions.assertEquals(expected, actual); }
@Test void testCreateWithBothKeyMapperAndValueMapperToADifferentType() { ImmutableMap<Integer, Integer> baseMap = ImmutableMap.of( 1, 1, 2, 2, 3, 3, 4, 4); ImmutableMap<String, String> expected = ImmutableMap.of( "1", "2", "4", "4", "9", "6", "16", "8"); ImmutableMap<String, String> actual = ImmutableMapFactory.create( baseMap, key -> String.valueOf(key * key), value -> String.valueOf(value * 2)); Assertions.assertEquals(expected, actual); }
@Test void testCreateWithBothKeyCreatorAndValueCreator() { ImmutableMap<Integer, Integer> baseMap = ImmutableMap.of( 2, 1, 4, 2, 6, 3, 8, 4); ImmutableMap<Integer, Integer> expected = ImmutableMap.of( 2, 3, 8, 6, 18, 9, 32, 12); ImmutableMap<Integer, Integer> actual = ImmutableMapFactory.create( baseMap, (key, value) -> key * value, (key, value) -> key + value); Assertions.assertEquals(expected, actual); }
@Test void testCreateWithBothKeyCreatorAndValueCreatorToADifferentType() { ImmutableMap<Integer, Integer> baseMap = ImmutableMap.of( 2, 1, 4, 2, 6, 3, 8, 4); ImmutableMap<String, String> expected = ImmutableMap.of( "2", "3", "8", "6", "18", "9", "32", "12"); ImmutableMap<String, String> actual = ImmutableMapFactory.create( baseMap, (key, value) -> String.valueOf(key * value), (key, value) -> String.valueOf(key + value)); Assertions.assertEquals(expected, actual); }