ImmutableMapFactory { public static <K, V> ImmutableMap<K, V> zip( List<K> keys, List<V> values) { Preconditions.checkArgument( keys.size() == values.size(), "Size of keys and values should match"); return ImmutableMapFactory.createFromKeys(keys, values.iterator()::next); }  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 testZip() { ImmutableList<String> keys = ImmutableList.of("a", "b", "c"); ImmutableList<Integer> values = ImmutableList.of(1, 2, 3); ImmutableMap<String, Integer> zipped = ImmutableMapFactory.zip(keys, values); Assertions.assertEquals(ImmutableSet.copyOf(keys), zipped.keySet()); Assertions.assertEquals(values, ImmutableList.copyOf(zipped.values())); }
@Test void zipThrowsForDifferentSizesLists() { ImmutableList<String> tooManyKeys = ImmutableList.of("a", "b", "c"); ImmutableList<Integer> notEnoughValues = ImmutableList.of(1, 2); Assertions.assertThrows( IllegalArgumentException.class, () -> ImmutableMapFactory.zip(tooManyKeys, notEnoughValues)); }