17dd252788645e940eada959bdde927426e2531c9Paul Duffin/*
27dd252788645e940eada959bdde927426e2531c9Paul Duffin * Copyright (C) 2008 The Guava Authors
37dd252788645e940eada959bdde927426e2531c9Paul Duffin *
47dd252788645e940eada959bdde927426e2531c9Paul Duffin * Licensed under the Apache License, Version 2.0 (the "License");
57dd252788645e940eada959bdde927426e2531c9Paul Duffin * you may not use this file except in compliance with the License.
67dd252788645e940eada959bdde927426e2531c9Paul Duffin * You may obtain a copy of the License at
77dd252788645e940eada959bdde927426e2531c9Paul Duffin *
87dd252788645e940eada959bdde927426e2531c9Paul Duffin * http://www.apache.org/licenses/LICENSE-2.0
97dd252788645e940eada959bdde927426e2531c9Paul Duffin *
107dd252788645e940eada959bdde927426e2531c9Paul Duffin * Unless required by applicable law or agreed to in writing, software
117dd252788645e940eada959bdde927426e2531c9Paul Duffin * distributed under the License is distributed on an "AS IS" BASIS,
127dd252788645e940eada959bdde927426e2531c9Paul Duffin * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
137dd252788645e940eada959bdde927426e2531c9Paul Duffin * See the License for the specific language governing permissions and
147dd252788645e940eada959bdde927426e2531c9Paul Duffin * limitations under the License.
157dd252788645e940eada959bdde927426e2531c9Paul Duffin */
167dd252788645e940eada959bdde927426e2531c9Paul Duffin
177dd252788645e940eada959bdde927426e2531c9Paul Duffinpackage com.google.common.collect;
187dd252788645e940eada959bdde927426e2531c9Paul Duffin
197dd252788645e940eada959bdde927426e2531c9Paul Duffinimport static com.google.common.collect.Maps.newHashMap;
207dd252788645e940eada959bdde927426e2531c9Paul Duffinimport static com.google.common.collect.testing.Helpers.mapEntry;
217dd252788645e940eada959bdde927426e2531c9Paul Duffinimport static com.google.common.collect.testing.features.CollectionFeature.ALLOWS_NULL_VALUES;
227dd252788645e940eada959bdde927426e2531c9Paul Duffinimport static com.google.common.collect.testing.features.CollectionFeature.SUPPORTS_REMOVE;
237dd252788645e940eada959bdde927426e2531c9Paul Duffinimport static com.google.common.collect.testing.google.AbstractMultisetSetCountTester.getSetCountDuplicateInitializingMethods;
240888a09821a98ac0680fad765217302858e70fa4Paul Duffinimport static com.google.common.collect.testing.google.MultisetCountTester.getCountDuplicateInitializingMethods;
257dd252788645e940eada959bdde927426e2531c9Paul Duffinimport static com.google.common.collect.testing.google.MultisetIteratorTester.getIteratorDuplicateInitializingMethods;
260888a09821a98ac0680fad765217302858e70fa4Paul Duffinimport static com.google.common.collect.testing.google.MultisetRemoveTester.getRemoveDuplicateInitializingMethods;
277dd252788645e940eada959bdde927426e2531c9Paul Duffinimport static java.lang.reflect.Proxy.newProxyInstance;
287dd252788645e940eada959bdde927426e2531c9Paul Duffin
297dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.annotations.GwtIncompatible;
307dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.base.Ascii;
317dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.base.Function;
327dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.base.Predicate;
337dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.base.Predicates;
347dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.base.Supplier;
357dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.collect.Maps.EntryTransformer;
367dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.collect.testing.SampleElements;
377dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.collect.testing.SetTestSuiteBuilder;
387dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.collect.testing.TestCollectionGenerator;
397dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.collect.testing.TestListGenerator;
407dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.collect.testing.TestStringSetGenerator;
417dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.collect.testing.features.CollectionFeature;
427dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.collect.testing.features.CollectionSize;
437dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.collect.testing.features.Feature;
447dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.collect.testing.features.MapFeature;
457dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.collect.testing.google.ListMultimapTestSuiteBuilder;
460888a09821a98ac0680fad765217302858e70fa4Paul Duffinimport com.google.common.collect.testing.google.MultimapFeature;
477dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.collect.testing.google.MultimapTestSuiteBuilder;
487dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.collect.testing.google.MultisetTestSuiteBuilder;
490888a09821a98ac0680fad765217302858e70fa4Paul Duffinimport com.google.common.collect.testing.google.SetMultimapTestSuiteBuilder;
507dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.collect.testing.google.TestListMultimapGenerator;
517dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.collect.testing.google.TestMultimapGenerator;
520888a09821a98ac0680fad765217302858e70fa4Paul Duffinimport com.google.common.collect.testing.google.TestSetMultimapGenerator;
537dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.collect.testing.google.TestStringListMultimapGenerator;
547dd252788645e940eada959bdde927426e2531c9Paul Duffinimport com.google.common.collect.testing.google.TestStringMultisetGenerator;
550888a09821a98ac0680fad765217302858e70fa4Paul Duffin
560888a09821a98ac0680fad765217302858e70fa4Paul Duffinimport junit.framework.Test;
570888a09821a98ac0680fad765217302858e70fa4Paul Duffinimport junit.framework.TestCase;
580888a09821a98ac0680fad765217302858e70fa4Paul Duffinimport junit.framework.TestSuite;
597dd252788645e940eada959bdde927426e2531c9Paul Duffin
607dd252788645e940eada959bdde927426e2531c9Paul Duffinimport java.lang.reflect.InvocationHandler;
617dd252788645e940eada959bdde927426e2531c9Paul Duffinimport java.lang.reflect.Method;
627dd252788645e940eada959bdde927426e2531c9Paul Duffinimport java.util.Collection;
637dd252788645e940eada959bdde927426e2531c9Paul Duffinimport java.util.List;
647dd252788645e940eada959bdde927426e2531c9Paul Duffinimport java.util.Map;
657dd252788645e940eada959bdde927426e2531c9Paul Duffinimport java.util.Map.Entry;
667dd252788645e940eada959bdde927426e2531c9Paul Duffinimport java.util.Set;
677dd252788645e940eada959bdde927426e2531c9Paul Duffinimport java.util.TreeSet;
687dd252788645e940eada959bdde927426e2531c9Paul Duffin
697dd252788645e940eada959bdde927426e2531c9Paul Duffin/**
707dd252788645e940eada959bdde927426e2531c9Paul Duffin * Run collection tests on wrappers from {@link Multimaps}.
717dd252788645e940eada959bdde927426e2531c9Paul Duffin *
727dd252788645e940eada959bdde927426e2531c9Paul Duffin * @author Jared Levy
737dd252788645e940eada959bdde927426e2531c9Paul Duffin */
747dd252788645e940eada959bdde927426e2531c9Paul Duffin@GwtIncompatible("suite") // TODO(cpovirk): set up collect/gwt/suites version
757dd252788645e940eada959bdde927426e2531c9Paul Duffinpublic class MultimapsCollectionTest extends TestCase {
767dd252788645e940eada959bdde927426e2531c9Paul Duffin
777dd252788645e940eada959bdde927426e2531c9Paul Duffin  private static final Feature<?>[] FOR_MAP_FEATURES_ONE = {
787dd252788645e940eada959bdde927426e2531c9Paul Duffin    CollectionSize.ONE,
797dd252788645e940eada959bdde927426e2531c9Paul Duffin    ALLOWS_NULL_VALUES,
807dd252788645e940eada959bdde927426e2531c9Paul Duffin    SUPPORTS_REMOVE,
810888a09821a98ac0680fad765217302858e70fa4Paul Duffin    CollectionFeature.SUPPORTS_ITERATOR_REMOVE
827dd252788645e940eada959bdde927426e2531c9Paul Duffin  };
837dd252788645e940eada959bdde927426e2531c9Paul Duffin
847dd252788645e940eada959bdde927426e2531c9Paul Duffin  private static final Feature<?>[] FOR_MAP_FEATURES_ANY = {
857dd252788645e940eada959bdde927426e2531c9Paul Duffin    CollectionSize.ANY,
867dd252788645e940eada959bdde927426e2531c9Paul Duffin    ALLOWS_NULL_VALUES,
877dd252788645e940eada959bdde927426e2531c9Paul Duffin    SUPPORTS_REMOVE,
880888a09821a98ac0680fad765217302858e70fa4Paul Duffin    CollectionFeature.SUPPORTS_ITERATOR_REMOVE,
897dd252788645e940eada959bdde927426e2531c9Paul Duffin    MultisetTestSuiteBuilder.NoRecurse.NO_ENTRY_SET,  // Cannot create entries with count > 1
907dd252788645e940eada959bdde927426e2531c9Paul Duffin  };
917dd252788645e940eada959bdde927426e2531c9Paul Duffin
927dd252788645e940eada959bdde927426e2531c9Paul Duffin  static final Supplier<TreeSet<String>> STRING_TREESET_FACTORY = new Supplier<TreeSet<String>>() {
937dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
947dd252788645e940eada959bdde927426e2531c9Paul Duffin    public TreeSet<String> get() {
957dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new TreeSet<String>(Ordering.natural().nullsLast());
967dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
977dd252788645e940eada959bdde927426e2531c9Paul Duffin  };
987dd252788645e940eada959bdde927426e2531c9Paul Duffin
997dd252788645e940eada959bdde927426e2531c9Paul Duffin  static void populateMultimapForGet(
1007dd252788645e940eada959bdde927426e2531c9Paul Duffin      Multimap<Integer, String> multimap, String[] elements) {
1017dd252788645e940eada959bdde927426e2531c9Paul Duffin    multimap.put(2, "foo");
1027dd252788645e940eada959bdde927426e2531c9Paul Duffin    for (String element : elements) {
1037dd252788645e940eada959bdde927426e2531c9Paul Duffin      multimap.put(3, element);
1047dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
1057dd252788645e940eada959bdde927426e2531c9Paul Duffin  }
1067dd252788645e940eada959bdde927426e2531c9Paul Duffin
1077dd252788645e940eada959bdde927426e2531c9Paul Duffin  static void populateMultimapForKeySet(
1087dd252788645e940eada959bdde927426e2531c9Paul Duffin      Multimap<String, Integer> multimap, String[] elements) {
1097dd252788645e940eada959bdde927426e2531c9Paul Duffin    for (String element : elements) {
1107dd252788645e940eada959bdde927426e2531c9Paul Duffin      multimap.put(element, 2);
1117dd252788645e940eada959bdde927426e2531c9Paul Duffin      multimap.put(element, 3);
1127dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
1137dd252788645e940eada959bdde927426e2531c9Paul Duffin  }
1147dd252788645e940eada959bdde927426e2531c9Paul Duffin
1157dd252788645e940eada959bdde927426e2531c9Paul Duffin  static void populateMultimapForValues(
1167dd252788645e940eada959bdde927426e2531c9Paul Duffin      Multimap<Integer, String> multimap, String[] elements) {
1177dd252788645e940eada959bdde927426e2531c9Paul Duffin    for (int i = 0; i < elements.length; i++) {
1187dd252788645e940eada959bdde927426e2531c9Paul Duffin      multimap.put(i % 2, elements[i]);
1197dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
1207dd252788645e940eada959bdde927426e2531c9Paul Duffin  }
1217dd252788645e940eada959bdde927426e2531c9Paul Duffin
1227dd252788645e940eada959bdde927426e2531c9Paul Duffin  static void populateMultimapForKeys(
1237dd252788645e940eada959bdde927426e2531c9Paul Duffin      Multimap<String, Integer> multimap, String[] elements) {
1247dd252788645e940eada959bdde927426e2531c9Paul Duffin    for (int i = 0; i < elements.length; i++) {
1257dd252788645e940eada959bdde927426e2531c9Paul Duffin      multimap.put(elements[i], i);
1267dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
1277dd252788645e940eada959bdde927426e2531c9Paul Duffin  }
1287dd252788645e940eada959bdde927426e2531c9Paul Duffin
1297dd252788645e940eada959bdde927426e2531c9Paul Duffin  /**
1307dd252788645e940eada959bdde927426e2531c9Paul Duffin   * Implements {@code Multimap.put()} -- and no other methods -- for a {@code
1317dd252788645e940eada959bdde927426e2531c9Paul Duffin   * Map} by ignoring all but the latest value for each key. This class exists
1327dd252788645e940eada959bdde927426e2531c9Paul Duffin   * only so that we can use
1337dd252788645e940eada959bdde927426e2531c9Paul Duffin   * {@link MultimapsCollectionTest#populateMultimapForGet(Multimap, String[])}
1347dd252788645e940eada959bdde927426e2531c9Paul Duffin   * and similar methods to populate a map to be passed to
1357dd252788645e940eada959bdde927426e2531c9Paul Duffin   * {@link Multimaps#forMap(Map)}. All tests should run against the result of
1367dd252788645e940eada959bdde927426e2531c9Paul Duffin   * {@link #build()}.
1377dd252788645e940eada959bdde927426e2531c9Paul Duffin   */
1387dd252788645e940eada959bdde927426e2531c9Paul Duffin  private static final class PopulatableMapAsMultimap<K, V>
1397dd252788645e940eada959bdde927426e2531c9Paul Duffin      extends ForwardingMultimap<K, V> {
1407dd252788645e940eada959bdde927426e2531c9Paul Duffin    final Map<K, V> map;
1417dd252788645e940eada959bdde927426e2531c9Paul Duffin    final SetMultimap<K, V> unusableDelegate;
1427dd252788645e940eada959bdde927426e2531c9Paul Duffin
1437dd252788645e940eada959bdde927426e2531c9Paul Duffin    static <K, V> PopulatableMapAsMultimap<K, V> create() {
1447dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new PopulatableMapAsMultimap<K, V>();
1457dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
1467dd252788645e940eada959bdde927426e2531c9Paul Duffin
1477dd252788645e940eada959bdde927426e2531c9Paul Duffin    @SuppressWarnings("unchecked")  // all methods throw immediately
1487dd252788645e940eada959bdde927426e2531c9Paul Duffin    PopulatableMapAsMultimap() {
1497dd252788645e940eada959bdde927426e2531c9Paul Duffin      this.map = newHashMap();
1507dd252788645e940eada959bdde927426e2531c9Paul Duffin      this.unusableDelegate = (SetMultimap<K, V>) newProxyInstance(
1517dd252788645e940eada959bdde927426e2531c9Paul Duffin          SetMultimap.class.getClassLoader(),
1527dd252788645e940eada959bdde927426e2531c9Paul Duffin          new Class<?>[] {SetMultimap.class},
1537dd252788645e940eada959bdde927426e2531c9Paul Duffin          new InvocationHandler() {
1547dd252788645e940eada959bdde927426e2531c9Paul Duffin            @Override
1557dd252788645e940eada959bdde927426e2531c9Paul Duffin            public Object invoke(Object proxy, Method method, Object[] args)
1567dd252788645e940eada959bdde927426e2531c9Paul Duffin                throws Throwable {
1577dd252788645e940eada959bdde927426e2531c9Paul Duffin              throw new UnsupportedOperationException();
1587dd252788645e940eada959bdde927426e2531c9Paul Duffin            }
1597dd252788645e940eada959bdde927426e2531c9Paul Duffin          });
1607dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
1617dd252788645e940eada959bdde927426e2531c9Paul Duffin
1627dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override protected Multimap<K, V> delegate() {
1637dd252788645e940eada959bdde927426e2531c9Paul Duffin      return unusableDelegate;
1647dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
1657dd252788645e940eada959bdde927426e2531c9Paul Duffin
1667dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override public boolean put(K key, V value) {
1677dd252788645e940eada959bdde927426e2531c9Paul Duffin      map.put(key, value);
1687dd252788645e940eada959bdde927426e2531c9Paul Duffin      return true;
1697dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
1707dd252788645e940eada959bdde927426e2531c9Paul Duffin
1717dd252788645e940eada959bdde927426e2531c9Paul Duffin    SetMultimap<K, V> build() {
1727dd252788645e940eada959bdde927426e2531c9Paul Duffin      return Multimaps.forMap(map);
1737dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
1747dd252788645e940eada959bdde927426e2531c9Paul Duffin  }
1757dd252788645e940eada959bdde927426e2531c9Paul Duffin
1767dd252788645e940eada959bdde927426e2531c9Paul Duffin  abstract static class TestEntriesGenerator
1777dd252788645e940eada959bdde927426e2531c9Paul Duffin      implements TestCollectionGenerator<Entry<String, Integer>> {
1787dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
1797dd252788645e940eada959bdde927426e2531c9Paul Duffin    public SampleElements<Entry<String, Integer>> samples() {
1807dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new SampleElements<Entry<String, Integer>>(
1817dd252788645e940eada959bdde927426e2531c9Paul Duffin          Maps.immutableEntry("bar", 1),
1827dd252788645e940eada959bdde927426e2531c9Paul Duffin          Maps.immutableEntry("bar", 2),
1837dd252788645e940eada959bdde927426e2531c9Paul Duffin          Maps.immutableEntry("foo", 3),
1847dd252788645e940eada959bdde927426e2531c9Paul Duffin          Maps.immutableEntry("bar", 3),
1857dd252788645e940eada959bdde927426e2531c9Paul Duffin          Maps.immutableEntry("cat", 2));
1867dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
1877dd252788645e940eada959bdde927426e2531c9Paul Duffin
1887dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
1897dd252788645e940eada959bdde927426e2531c9Paul Duffin    public Collection<Entry<String, Integer>> create(Object... elements) {
1907dd252788645e940eada959bdde927426e2531c9Paul Duffin      Multimap<String, Integer> multimap = createMultimap();
1917dd252788645e940eada959bdde927426e2531c9Paul Duffin      for (Object element : elements) {
1927dd252788645e940eada959bdde927426e2531c9Paul Duffin        @SuppressWarnings("unchecked")
1937dd252788645e940eada959bdde927426e2531c9Paul Duffin        Entry<String, Integer> entry = (Entry<String, Integer>) element;
1947dd252788645e940eada959bdde927426e2531c9Paul Duffin        multimap.put(entry.getKey(), entry.getValue());
1957dd252788645e940eada959bdde927426e2531c9Paul Duffin      }
1967dd252788645e940eada959bdde927426e2531c9Paul Duffin      return multimap.entries();
1977dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
1987dd252788645e940eada959bdde927426e2531c9Paul Duffin
1997dd252788645e940eada959bdde927426e2531c9Paul Duffin    abstract Multimap<String, Integer> createMultimap();
2007dd252788645e940eada959bdde927426e2531c9Paul Duffin
2017dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
2027dd252788645e940eada959bdde927426e2531c9Paul Duffin    @SuppressWarnings("unchecked")
2037dd252788645e940eada959bdde927426e2531c9Paul Duffin    public Entry<String, Integer>[] createArray(int length) {
2047dd252788645e940eada959bdde927426e2531c9Paul Duffin      return (Entry<String, Integer>[]) new Entry<?, ?>[length];
2057dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
2067dd252788645e940eada959bdde927426e2531c9Paul Duffin
2077dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
2087dd252788645e940eada959bdde927426e2531c9Paul Duffin    public List<Entry<String, Integer>> order(
2097dd252788645e940eada959bdde927426e2531c9Paul Duffin        List<Entry<String, Integer>> insertionOrder) {
2107dd252788645e940eada959bdde927426e2531c9Paul Duffin      return insertionOrder;
2117dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
2127dd252788645e940eada959bdde927426e2531c9Paul Duffin  }
2137dd252788645e940eada959bdde927426e2531c9Paul Duffin
2147dd252788645e940eada959bdde927426e2531c9Paul Duffin  public abstract static class TestEntriesListGenerator
2157dd252788645e940eada959bdde927426e2531c9Paul Duffin      extends TestEntriesGenerator
2167dd252788645e940eada959bdde927426e2531c9Paul Duffin      implements TestListGenerator<Entry<String, Integer>> {
2177dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override public List<Entry<String, Integer>> create(Object... elements) {
2187dd252788645e940eada959bdde927426e2531c9Paul Duffin      return (List<Entry<String, Integer>>) super.create(elements);
2197dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
2207dd252788645e940eada959bdde927426e2531c9Paul Duffin  }
2217dd252788645e940eada959bdde927426e2531c9Paul Duffin
2227dd252788645e940eada959bdde927426e2531c9Paul Duffin  private static final Predicate<Map.Entry<Integer, String>> FILTER_GET_PREDICATE
2237dd252788645e940eada959bdde927426e2531c9Paul Duffin      = new Predicate<Map.Entry<Integer, String>>() {
2247dd252788645e940eada959bdde927426e2531c9Paul Duffin        @Override public boolean apply(Entry<Integer, String> entry) {
2257dd252788645e940eada959bdde927426e2531c9Paul Duffin          return !"badvalue".equals(entry.getValue()) && 55556 != entry.getKey();
2267dd252788645e940eada959bdde927426e2531c9Paul Duffin        }
2277dd252788645e940eada959bdde927426e2531c9Paul Duffin    };
2287dd252788645e940eada959bdde927426e2531c9Paul Duffin
2297dd252788645e940eada959bdde927426e2531c9Paul Duffin  private static final Predicate<Map.Entry<String, Integer>> FILTER_KEYSET_PREDICATE
2307dd252788645e940eada959bdde927426e2531c9Paul Duffin    = new Predicate<Map.Entry<String, Integer>>() {
2317dd252788645e940eada959bdde927426e2531c9Paul Duffin      @Override public boolean apply(Entry<String, Integer> entry) {
2327dd252788645e940eada959bdde927426e2531c9Paul Duffin        return !"badkey".equals(entry.getKey()) && 55556 != entry.getValue();
2337dd252788645e940eada959bdde927426e2531c9Paul Duffin      }
2347dd252788645e940eada959bdde927426e2531c9Paul Duffin  };
2357dd252788645e940eada959bdde927426e2531c9Paul Duffin
2367dd252788645e940eada959bdde927426e2531c9Paul Duffin  public static Test suite() {
2377dd252788645e940eada959bdde927426e2531c9Paul Duffin    TestSuite suite = new TestSuite();
2387dd252788645e940eada959bdde927426e2531c9Paul Duffin
2390888a09821a98ac0680fad765217302858e70fa4Paul Duffin    suite.addTest(transformSuite());
2400888a09821a98ac0680fad765217302858e70fa4Paul Duffin    suite.addTest(filterSuite());
2410888a09821a98ac0680fad765217302858e70fa4Paul Duffin
2427dd252788645e940eada959bdde927426e2531c9Paul Duffin    suite.addTest(ListMultimapTestSuiteBuilder.using(new TestStringListMultimapGenerator() {
2437dd252788645e940eada959bdde927426e2531c9Paul Duffin        @Override
2447dd252788645e940eada959bdde927426e2531c9Paul Duffin        protected ListMultimap<String, String> create(Entry<String, String>[] entries) {
2457dd252788645e940eada959bdde927426e2531c9Paul Duffin          ListMultimap<String, String> multimap = Multimaps.synchronizedListMultimap(
2467dd252788645e940eada959bdde927426e2531c9Paul Duffin              ArrayListMultimap.<String, String> create());
2477dd252788645e940eada959bdde927426e2531c9Paul Duffin          for (Entry<String, String> entry : entries) {
2487dd252788645e940eada959bdde927426e2531c9Paul Duffin            multimap.put(entry.getKey(), entry.getValue());
2497dd252788645e940eada959bdde927426e2531c9Paul Duffin          }
2507dd252788645e940eada959bdde927426e2531c9Paul Duffin          return multimap;
2517dd252788645e940eada959bdde927426e2531c9Paul Duffin        }
2527dd252788645e940eada959bdde927426e2531c9Paul Duffin      })
2537dd252788645e940eada959bdde927426e2531c9Paul Duffin      .named("synchronized ArrayListMultimap")
2547dd252788645e940eada959bdde927426e2531c9Paul Duffin      .withFeatures(
2557dd252788645e940eada959bdde927426e2531c9Paul Duffin          MapFeature.ALLOWS_NULL_KEYS,
2567dd252788645e940eada959bdde927426e2531c9Paul Duffin          MapFeature.ALLOWS_NULL_VALUES,
2570888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_ANY_NULL_QUERIES,
2587dd252788645e940eada959bdde927426e2531c9Paul Duffin          MapFeature.GENERAL_PURPOSE,
2597dd252788645e940eada959bdde927426e2531c9Paul Duffin          MapFeature.FAILS_FAST_ON_CONCURRENT_MODIFICATION,
2600888a09821a98ac0680fad765217302858e70fa4Paul Duffin          CollectionFeature.SUPPORTS_ITERATOR_REMOVE,
2617dd252788645e940eada959bdde927426e2531c9Paul Duffin          CollectionSize.ANY)
2627dd252788645e940eada959bdde927426e2531c9Paul Duffin      .createTestSuite());
2637dd252788645e940eada959bdde927426e2531c9Paul Duffin
2647dd252788645e940eada959bdde927426e2531c9Paul Duffin    suite.addTest(SetTestSuiteBuilder.using(
2657dd252788645e940eada959bdde927426e2531c9Paul Duffin        new TestStringSetGenerator() {
2667dd252788645e940eada959bdde927426e2531c9Paul Duffin          @Override protected Set<String> create(String[] elements) {
2677dd252788645e940eada959bdde927426e2531c9Paul Duffin            PopulatableMapAsMultimap<Integer, String> multimap
2687dd252788645e940eada959bdde927426e2531c9Paul Duffin                = PopulatableMapAsMultimap.create();
2697dd252788645e940eada959bdde927426e2531c9Paul Duffin            populateMultimapForGet(multimap, elements);
2707dd252788645e940eada959bdde927426e2531c9Paul Duffin            return multimap.build().get(3);
2717dd252788645e940eada959bdde927426e2531c9Paul Duffin          }
2727dd252788645e940eada959bdde927426e2531c9Paul Duffin        })
2737dd252788645e940eada959bdde927426e2531c9Paul Duffin        .named("Multimaps.forMap.get")
2747dd252788645e940eada959bdde927426e2531c9Paul Duffin        .withFeatures(FOR_MAP_FEATURES_ONE)
2757dd252788645e940eada959bdde927426e2531c9Paul Duffin        .createTestSuite());
2767dd252788645e940eada959bdde927426e2531c9Paul Duffin
2777dd252788645e940eada959bdde927426e2531c9Paul Duffin    suite.addTest(SetTestSuiteBuilder.using(
2787dd252788645e940eada959bdde927426e2531c9Paul Duffin        new TestStringSetGenerator() {
2797dd252788645e940eada959bdde927426e2531c9Paul Duffin          @Override protected Set<String> create(String[] elements) {
2807dd252788645e940eada959bdde927426e2531c9Paul Duffin            PopulatableMapAsMultimap<String, Integer> multimap
2817dd252788645e940eada959bdde927426e2531c9Paul Duffin                = PopulatableMapAsMultimap.create();
2827dd252788645e940eada959bdde927426e2531c9Paul Duffin            populateMultimapForKeySet(multimap, elements);
2837dd252788645e940eada959bdde927426e2531c9Paul Duffin            return multimap.build().keySet();
2847dd252788645e940eada959bdde927426e2531c9Paul Duffin          }
2857dd252788645e940eada959bdde927426e2531c9Paul Duffin        })
2867dd252788645e940eada959bdde927426e2531c9Paul Duffin        .named("Multimaps.forMap.keySet")
2877dd252788645e940eada959bdde927426e2531c9Paul Duffin        .withFeatures(FOR_MAP_FEATURES_ANY)
2887dd252788645e940eada959bdde927426e2531c9Paul Duffin        .createTestSuite());
2897dd252788645e940eada959bdde927426e2531c9Paul Duffin
2907dd252788645e940eada959bdde927426e2531c9Paul Duffin    // TODO: use collection testers on Multimaps.forMap.values
2917dd252788645e940eada959bdde927426e2531c9Paul Duffin
2927dd252788645e940eada959bdde927426e2531c9Paul Duffin    suite.addTest(MultisetTestSuiteBuilder.using(
2937dd252788645e940eada959bdde927426e2531c9Paul Duffin        new TestStringMultisetGenerator() {
2947dd252788645e940eada959bdde927426e2531c9Paul Duffin          @Override protected Multiset<String> create(String[] elements) {
2957dd252788645e940eada959bdde927426e2531c9Paul Duffin            PopulatableMapAsMultimap<String, Integer> multimap
2967dd252788645e940eada959bdde927426e2531c9Paul Duffin                = PopulatableMapAsMultimap.create();
2977dd252788645e940eada959bdde927426e2531c9Paul Duffin            populateMultimapForKeys(multimap, elements);
2987dd252788645e940eada959bdde927426e2531c9Paul Duffin            return multimap.build().keys();
2997dd252788645e940eada959bdde927426e2531c9Paul Duffin          }
3007dd252788645e940eada959bdde927426e2531c9Paul Duffin        })
3017dd252788645e940eada959bdde927426e2531c9Paul Duffin        .named("Multimaps.forMap.keys")
3027dd252788645e940eada959bdde927426e2531c9Paul Duffin        .withFeatures(FOR_MAP_FEATURES_ANY)
3030888a09821a98ac0680fad765217302858e70fa4Paul Duffin        .suppressing(getCountDuplicateInitializingMethods())
3047dd252788645e940eada959bdde927426e2531c9Paul Duffin        .suppressing(getSetCountDuplicateInitializingMethods())
3057dd252788645e940eada959bdde927426e2531c9Paul Duffin        .suppressing(getIteratorDuplicateInitializingMethods())
3060888a09821a98ac0680fad765217302858e70fa4Paul Duffin        .suppressing(getRemoveDuplicateInitializingMethods())
3077dd252788645e940eada959bdde927426e2531c9Paul Duffin        .createTestSuite());
3087dd252788645e940eada959bdde927426e2531c9Paul Duffin
3097dd252788645e940eada959bdde927426e2531c9Paul Duffin    // TODO: use collection testers on Multimaps.forMap.entries
3107dd252788645e940eada959bdde927426e2531c9Paul Duffin
3117dd252788645e940eada959bdde927426e2531c9Paul Duffin    return suite;
3127dd252788645e940eada959bdde927426e2531c9Paul Duffin  }
3137dd252788645e940eada959bdde927426e2531c9Paul Duffin
3147dd252788645e940eada959bdde927426e2531c9Paul Duffin  static abstract class TransformedMultimapGenerator<M extends Multimap<String, String>>
3157dd252788645e940eada959bdde927426e2531c9Paul Duffin      implements TestMultimapGenerator<String, String, M> {
3167dd252788645e940eada959bdde927426e2531c9Paul Duffin
3177dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
3187dd252788645e940eada959bdde927426e2531c9Paul Duffin    public String[] createKeyArray(int length) {
3197dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new String[length];
3207dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
3217dd252788645e940eada959bdde927426e2531c9Paul Duffin
3227dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
3237dd252788645e940eada959bdde927426e2531c9Paul Duffin    public String[] createValueArray(int length) {
3247dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new String[length];
3257dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
3267dd252788645e940eada959bdde927426e2531c9Paul Duffin
3277dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
3287dd252788645e940eada959bdde927426e2531c9Paul Duffin    public SampleElements<String> sampleKeys() {
3297dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new SampleElements<String>("one", "two", "three", "four", "five");
3307dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
3317dd252788645e940eada959bdde927426e2531c9Paul Duffin
3327dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
3337dd252788645e940eada959bdde927426e2531c9Paul Duffin    public SampleElements<String> sampleValues() {
3347dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new SampleElements<String>("january", "february", "march", "april", "may");
3357dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
3367dd252788645e940eada959bdde927426e2531c9Paul Duffin
3377dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
3387dd252788645e940eada959bdde927426e2531c9Paul Duffin    public Collection<String> createCollection(Iterable<? extends String> values) {
3397dd252788645e940eada959bdde927426e2531c9Paul Duffin      return Lists.newArrayList(values);
3407dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
3417dd252788645e940eada959bdde927426e2531c9Paul Duffin
3427dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
3437dd252788645e940eada959bdde927426e2531c9Paul Duffin    public SampleElements<Entry<String, String>> samples() {
3447dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new SampleElements<Entry<String, String>>(
3457dd252788645e940eada959bdde927426e2531c9Paul Duffin          mapEntry("one", "january"),
3467dd252788645e940eada959bdde927426e2531c9Paul Duffin          mapEntry("two", "february"),
3477dd252788645e940eada959bdde927426e2531c9Paul Duffin          mapEntry("three", "march"),
3487dd252788645e940eada959bdde927426e2531c9Paul Duffin          mapEntry("four", "april"),
3497dd252788645e940eada959bdde927426e2531c9Paul Duffin          mapEntry("five", "may"));
3507dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
3517dd252788645e940eada959bdde927426e2531c9Paul Duffin
3527dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
3537dd252788645e940eada959bdde927426e2531c9Paul Duffin    public M create(Object... elements) {
3547dd252788645e940eada959bdde927426e2531c9Paul Duffin      Multimap<String, String> multimap = ArrayListMultimap.create();
3557dd252788645e940eada959bdde927426e2531c9Paul Duffin      for (Object o : elements) {
3567dd252788645e940eada959bdde927426e2531c9Paul Duffin        @SuppressWarnings("unchecked")
3577dd252788645e940eada959bdde927426e2531c9Paul Duffin        Entry<String, String> entry = (Entry<String, String>) o;
3587dd252788645e940eada959bdde927426e2531c9Paul Duffin        multimap.put(entry.getKey(), Ascii.toUpperCase(entry.getValue()));
3597dd252788645e940eada959bdde927426e2531c9Paul Duffin      }
3607dd252788645e940eada959bdde927426e2531c9Paul Duffin      return transform(multimap);
3617dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
3627dd252788645e940eada959bdde927426e2531c9Paul Duffin
3637dd252788645e940eada959bdde927426e2531c9Paul Duffin    abstract M transform(Multimap<String, String> multimap);
3647dd252788645e940eada959bdde927426e2531c9Paul Duffin
3657dd252788645e940eada959bdde927426e2531c9Paul Duffin    @SuppressWarnings("unchecked")
3667dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
3677dd252788645e940eada959bdde927426e2531c9Paul Duffin    public Entry<String, String>[] createArray(int length) {
3687dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new Entry[length];
3697dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
3707dd252788645e940eada959bdde927426e2531c9Paul Duffin
3717dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
3727dd252788645e940eada959bdde927426e2531c9Paul Duffin    public Iterable<Entry<String, String>> order(List<Entry<String, String>> insertionOrder) {
3737dd252788645e940eada959bdde927426e2531c9Paul Duffin      return insertionOrder;
3747dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
3757dd252788645e940eada959bdde927426e2531c9Paul Duffin
3767dd252788645e940eada959bdde927426e2531c9Paul Duffin    static final Function<String, String> FUNCTION = new Function<String, String>() {
3777dd252788645e940eada959bdde927426e2531c9Paul Duffin      @Override
3787dd252788645e940eada959bdde927426e2531c9Paul Duffin      public String apply(String value) {
3797dd252788645e940eada959bdde927426e2531c9Paul Duffin        return Ascii.toLowerCase(value);
3807dd252788645e940eada959bdde927426e2531c9Paul Duffin      }
3817dd252788645e940eada959bdde927426e2531c9Paul Duffin    };
3827dd252788645e940eada959bdde927426e2531c9Paul Duffin
3837dd252788645e940eada959bdde927426e2531c9Paul Duffin    static final EntryTransformer<String, String, String> ENTRY_TRANSFORMER =
3847dd252788645e940eada959bdde927426e2531c9Paul Duffin        new EntryTransformer<String, String, String>() {
3857dd252788645e940eada959bdde927426e2531c9Paul Duffin      @Override
3867dd252788645e940eada959bdde927426e2531c9Paul Duffin      public String transformEntry(String key, String value) {
3877dd252788645e940eada959bdde927426e2531c9Paul Duffin        return Ascii.toLowerCase(value);
3887dd252788645e940eada959bdde927426e2531c9Paul Duffin      }
3897dd252788645e940eada959bdde927426e2531c9Paul Duffin    };
3907dd252788645e940eada959bdde927426e2531c9Paul Duffin  }
3917dd252788645e940eada959bdde927426e2531c9Paul Duffin
3927dd252788645e940eada959bdde927426e2531c9Paul Duffin  static abstract class TransformedListMultimapGenerator
3937dd252788645e940eada959bdde927426e2531c9Paul Duffin      extends TransformedMultimapGenerator<ListMultimap<String, String>>
3947dd252788645e940eada959bdde927426e2531c9Paul Duffin      implements TestListMultimapGenerator<String, String> {
3957dd252788645e940eada959bdde927426e2531c9Paul Duffin  }
3967dd252788645e940eada959bdde927426e2531c9Paul Duffin
3977dd252788645e940eada959bdde927426e2531c9Paul Duffin  private static Test transformSuite() {
3987dd252788645e940eada959bdde927426e2531c9Paul Duffin    TestSuite suite = new TestSuite("Multimaps.transform*");
3997dd252788645e940eada959bdde927426e2531c9Paul Duffin    suite.addTest(MultimapTestSuiteBuilder.using(
4007dd252788645e940eada959bdde927426e2531c9Paul Duffin        new TransformedMultimapGenerator<Multimap<String,String>>() {
4017dd252788645e940eada959bdde927426e2531c9Paul Duffin          @Override
4027dd252788645e940eada959bdde927426e2531c9Paul Duffin          Multimap<String, String> transform(Multimap<String, String> multimap) {
4037dd252788645e940eada959bdde927426e2531c9Paul Duffin            return Multimaps.transformValues(multimap, FUNCTION);
4047dd252788645e940eada959bdde927426e2531c9Paul Duffin          }
4057dd252788645e940eada959bdde927426e2531c9Paul Duffin        })
4067dd252788645e940eada959bdde927426e2531c9Paul Duffin        .named("Multimaps.transformValues[Multimap]")
4077dd252788645e940eada959bdde927426e2531c9Paul Duffin        .withFeatures(
4087dd252788645e940eada959bdde927426e2531c9Paul Duffin            CollectionSize.ANY,
4097dd252788645e940eada959bdde927426e2531c9Paul Duffin            MapFeature.SUPPORTS_REMOVE,
4100888a09821a98ac0680fad765217302858e70fa4Paul Duffin            CollectionFeature.SUPPORTS_ITERATOR_REMOVE,
4110888a09821a98ac0680fad765217302858e70fa4Paul Duffin            MapFeature.ALLOWS_NULL_KEYS,
4120888a09821a98ac0680fad765217302858e70fa4Paul Duffin            MapFeature.ALLOWS_ANY_NULL_QUERIES)
4137dd252788645e940eada959bdde927426e2531c9Paul Duffin        .createTestSuite());
4147dd252788645e940eada959bdde927426e2531c9Paul Duffin    suite.addTest(MultimapTestSuiteBuilder.using(
4157dd252788645e940eada959bdde927426e2531c9Paul Duffin        new TransformedMultimapGenerator<Multimap<String,String>>() {
4167dd252788645e940eada959bdde927426e2531c9Paul Duffin          @Override
4177dd252788645e940eada959bdde927426e2531c9Paul Duffin          Multimap<String, String> transform(Multimap<String, String> multimap) {
4187dd252788645e940eada959bdde927426e2531c9Paul Duffin            return Multimaps.transformEntries(multimap, ENTRY_TRANSFORMER);
4197dd252788645e940eada959bdde927426e2531c9Paul Duffin          }
4207dd252788645e940eada959bdde927426e2531c9Paul Duffin        })
4217dd252788645e940eada959bdde927426e2531c9Paul Duffin        .named("Multimaps.transformEntries[Multimap]")
4227dd252788645e940eada959bdde927426e2531c9Paul Duffin        .withFeatures(
4237dd252788645e940eada959bdde927426e2531c9Paul Duffin            CollectionSize.ANY,
4247dd252788645e940eada959bdde927426e2531c9Paul Duffin            MapFeature.SUPPORTS_REMOVE,
4250888a09821a98ac0680fad765217302858e70fa4Paul Duffin            CollectionFeature.SUPPORTS_ITERATOR_REMOVE,
4260888a09821a98ac0680fad765217302858e70fa4Paul Duffin            MapFeature.ALLOWS_NULL_KEYS,
4270888a09821a98ac0680fad765217302858e70fa4Paul Duffin            MapFeature.ALLOWS_ANY_NULL_QUERIES)
4287dd252788645e940eada959bdde927426e2531c9Paul Duffin        .createTestSuite());
4297dd252788645e940eada959bdde927426e2531c9Paul Duffin    suite.addTest(ListMultimapTestSuiteBuilder.using(new TransformedListMultimapGenerator() {
4307dd252788645e940eada959bdde927426e2531c9Paul Duffin          @Override
4317dd252788645e940eada959bdde927426e2531c9Paul Duffin          ListMultimap<String, String> transform(Multimap<String, String> multimap) {
4327dd252788645e940eada959bdde927426e2531c9Paul Duffin            return Multimaps.transformValues((ListMultimap<String, String>) multimap, FUNCTION);
4337dd252788645e940eada959bdde927426e2531c9Paul Duffin          }
4347dd252788645e940eada959bdde927426e2531c9Paul Duffin        })
4357dd252788645e940eada959bdde927426e2531c9Paul Duffin        .named("Multimaps.transformValues[ListMultimap]")
4367dd252788645e940eada959bdde927426e2531c9Paul Duffin        .withFeatures(
4377dd252788645e940eada959bdde927426e2531c9Paul Duffin            CollectionSize.ANY,
4387dd252788645e940eada959bdde927426e2531c9Paul Duffin            MapFeature.SUPPORTS_REMOVE,
4390888a09821a98ac0680fad765217302858e70fa4Paul Duffin            CollectionFeature.SUPPORTS_ITERATOR_REMOVE,
4400888a09821a98ac0680fad765217302858e70fa4Paul Duffin            MapFeature.ALLOWS_NULL_KEYS,
4410888a09821a98ac0680fad765217302858e70fa4Paul Duffin            MapFeature.ALLOWS_ANY_NULL_QUERIES)
4427dd252788645e940eada959bdde927426e2531c9Paul Duffin        .createTestSuite());
4437dd252788645e940eada959bdde927426e2531c9Paul Duffin    suite.addTest(ListMultimapTestSuiteBuilder.using(new TransformedListMultimapGenerator() {
4447dd252788645e940eada959bdde927426e2531c9Paul Duffin          @Override
4457dd252788645e940eada959bdde927426e2531c9Paul Duffin          ListMultimap<String, String> transform(Multimap<String, String> multimap) {
4467dd252788645e940eada959bdde927426e2531c9Paul Duffin            return Multimaps.transformEntries(
4477dd252788645e940eada959bdde927426e2531c9Paul Duffin                (ListMultimap<String, String>) multimap, ENTRY_TRANSFORMER);
4487dd252788645e940eada959bdde927426e2531c9Paul Duffin          }
4497dd252788645e940eada959bdde927426e2531c9Paul Duffin        })
4507dd252788645e940eada959bdde927426e2531c9Paul Duffin        .named("Multimaps.transformEntries[ListMultimap]")
4517dd252788645e940eada959bdde927426e2531c9Paul Duffin        .withFeatures(
4527dd252788645e940eada959bdde927426e2531c9Paul Duffin            CollectionSize.ANY,
4537dd252788645e940eada959bdde927426e2531c9Paul Duffin            MapFeature.SUPPORTS_REMOVE,
4540888a09821a98ac0680fad765217302858e70fa4Paul Duffin            CollectionFeature.SUPPORTS_ITERATOR_REMOVE,
4550888a09821a98ac0680fad765217302858e70fa4Paul Duffin            MapFeature.ALLOWS_NULL_KEYS,
4560888a09821a98ac0680fad765217302858e70fa4Paul Duffin            MapFeature.ALLOWS_ANY_NULL_QUERIES)
4577dd252788645e940eada959bdde927426e2531c9Paul Duffin        .createTestSuite());
4587dd252788645e940eada959bdde927426e2531c9Paul Duffin
4597dd252788645e940eada959bdde927426e2531c9Paul Duffin    // TODO: use collection testers on Multimaps.forMap.entries
4607dd252788645e940eada959bdde927426e2531c9Paul Duffin
4617dd252788645e940eada959bdde927426e2531c9Paul Duffin    return suite;
4627dd252788645e940eada959bdde927426e2531c9Paul Duffin  }
4637dd252788645e940eada959bdde927426e2531c9Paul Duffin
4640888a09821a98ac0680fad765217302858e70fa4Paul Duffin  static abstract class TestFilteredMultimapGenerator<M extends Multimap<String, Integer>>
4650888a09821a98ac0680fad765217302858e70fa4Paul Duffin      implements TestMultimapGenerator<String, Integer, M> {
4667dd252788645e940eada959bdde927426e2531c9Paul Duffin
4677dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
4687dd252788645e940eada959bdde927426e2531c9Paul Duffin    public SampleElements<Entry<String, Integer>> samples() {
4697dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new SampleElements<Entry<String, Integer>>(
4707dd252788645e940eada959bdde927426e2531c9Paul Duffin          mapEntry("one", 114),
4717dd252788645e940eada959bdde927426e2531c9Paul Duffin          mapEntry("two", 37),
4727dd252788645e940eada959bdde927426e2531c9Paul Duffin          mapEntry("three", 42),
4737dd252788645e940eada959bdde927426e2531c9Paul Duffin          mapEntry("four", 19),
4747dd252788645e940eada959bdde927426e2531c9Paul Duffin          mapEntry("five", 82));
4757dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
4767dd252788645e940eada959bdde927426e2531c9Paul Duffin
4777dd252788645e940eada959bdde927426e2531c9Paul Duffin    @SuppressWarnings("unchecked")
4787dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
4797dd252788645e940eada959bdde927426e2531c9Paul Duffin    public Entry<String, Integer>[] createArray(int length) {
4807dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new Entry[length];
4817dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
4827dd252788645e940eada959bdde927426e2531c9Paul Duffin
4837dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
4847dd252788645e940eada959bdde927426e2531c9Paul Duffin    public Iterable<Entry<String, Integer>> order(List<Entry<String, Integer>> insertionOrder) {
4857dd252788645e940eada959bdde927426e2531c9Paul Duffin      return insertionOrder;
4867dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
4877dd252788645e940eada959bdde927426e2531c9Paul Duffin
4887dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
4897dd252788645e940eada959bdde927426e2531c9Paul Duffin    public String[] createKeyArray(int length) {
4907dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new String[length];
4917dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
4927dd252788645e940eada959bdde927426e2531c9Paul Duffin
4937dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
4947dd252788645e940eada959bdde927426e2531c9Paul Duffin    public Integer[] createValueArray(int length) {
4957dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new Integer[length];
4967dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
4977dd252788645e940eada959bdde927426e2531c9Paul Duffin
4987dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
4997dd252788645e940eada959bdde927426e2531c9Paul Duffin    public SampleElements<String> sampleKeys() {
5007dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new SampleElements<String>("one", "two", "three", "four", "five");
5017dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
5027dd252788645e940eada959bdde927426e2531c9Paul Duffin
5037dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
5047dd252788645e940eada959bdde927426e2531c9Paul Duffin    public SampleElements<Integer> sampleValues() {
5057dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new SampleElements<Integer>(114, 37, 42, 19, 82);
5067dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
5070888a09821a98ac0680fad765217302858e70fa4Paul Duffin  }
5080888a09821a98ac0680fad765217302858e70fa4Paul Duffin
5090888a09821a98ac0680fad765217302858e70fa4Paul Duffin  static abstract class FilteredSetMultimapGenerator
5100888a09821a98ac0680fad765217302858e70fa4Paul Duffin      extends TestFilteredMultimapGenerator<SetMultimap<String, Integer>>
5110888a09821a98ac0680fad765217302858e70fa4Paul Duffin      implements TestSetMultimapGenerator<String, Integer> {
5120888a09821a98ac0680fad765217302858e70fa4Paul Duffin
5130888a09821a98ac0680fad765217302858e70fa4Paul Duffin
5140888a09821a98ac0680fad765217302858e70fa4Paul Duffin    abstract SetMultimap<String, Integer> filter(SetMultimap<String, Integer> multimap);
5150888a09821a98ac0680fad765217302858e70fa4Paul Duffin
5160888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
5170888a09821a98ac0680fad765217302858e70fa4Paul Duffin    public SetMultimap<String, Integer> create(Object... elements) {
5180888a09821a98ac0680fad765217302858e70fa4Paul Duffin      SetMultimap<String, Integer> multimap = LinkedHashMultimap.create();
5190888a09821a98ac0680fad765217302858e70fa4Paul Duffin      for (Object o : elements) {
5200888a09821a98ac0680fad765217302858e70fa4Paul Duffin        @SuppressWarnings("unchecked")
5210888a09821a98ac0680fad765217302858e70fa4Paul Duffin        Entry<String, Integer> entry = (Entry<String, Integer>) o;
5220888a09821a98ac0680fad765217302858e70fa4Paul Duffin        multimap.put(entry.getKey(), entry.getValue());
5230888a09821a98ac0680fad765217302858e70fa4Paul Duffin      }
5240888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return filter(multimap);
5250888a09821a98ac0680fad765217302858e70fa4Paul Duffin    }
5267dd252788645e940eada959bdde927426e2531c9Paul Duffin
5277dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
5287dd252788645e940eada959bdde927426e2531c9Paul Duffin    public Collection<Integer> createCollection(Iterable<? extends Integer> values) {
5297dd252788645e940eada959bdde927426e2531c9Paul Duffin      return Sets.newLinkedHashSet(values);
5307dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
5317dd252788645e940eada959bdde927426e2531c9Paul Duffin  }
5320888a09821a98ac0680fad765217302858e70fa4Paul Duffin
5330888a09821a98ac0680fad765217302858e70fa4Paul Duffin  static abstract class FilteredListMultimapGenerator
5340888a09821a98ac0680fad765217302858e70fa4Paul Duffin      extends TestFilteredMultimapGenerator<ListMultimap<String, Integer>>
5350888a09821a98ac0680fad765217302858e70fa4Paul Duffin      implements TestListMultimapGenerator<String, Integer> {
5360888a09821a98ac0680fad765217302858e70fa4Paul Duffin
5370888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
5380888a09821a98ac0680fad765217302858e70fa4Paul Duffin    public ListMultimap<String, Integer> create(Object... elements) {
5390888a09821a98ac0680fad765217302858e70fa4Paul Duffin      ListMultimap<String, Integer> multimap = LinkedListMultimap.create();
5400888a09821a98ac0680fad765217302858e70fa4Paul Duffin      for (Object o : elements) {
5410888a09821a98ac0680fad765217302858e70fa4Paul Duffin        @SuppressWarnings("unchecked")
5420888a09821a98ac0680fad765217302858e70fa4Paul Duffin        Entry<String, Integer> entry = (Entry<String, Integer>) o;
5430888a09821a98ac0680fad765217302858e70fa4Paul Duffin        multimap.put(entry.getKey(), entry.getValue());
5440888a09821a98ac0680fad765217302858e70fa4Paul Duffin      }
5450888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return filter(multimap);
5460888a09821a98ac0680fad765217302858e70fa4Paul Duffin    }
5470888a09821a98ac0680fad765217302858e70fa4Paul Duffin
5480888a09821a98ac0680fad765217302858e70fa4Paul Duffin    abstract ListMultimap<String, Integer> filter(ListMultimap<String, Integer> multimap);
5490888a09821a98ac0680fad765217302858e70fa4Paul Duffin
5500888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
5510888a09821a98ac0680fad765217302858e70fa4Paul Duffin    public Collection<Integer> createCollection(Iterable<? extends Integer> values) {
5520888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return Lists.newArrayList(values);
5530888a09821a98ac0680fad765217302858e70fa4Paul Duffin    }
5540888a09821a98ac0680fad765217302858e70fa4Paul Duffin  }
5557dd252788645e940eada959bdde927426e2531c9Paul Duffin
5560888a09821a98ac0680fad765217302858e70fa4Paul Duffin  private static Test filterSuite() {
5577dd252788645e940eada959bdde927426e2531c9Paul Duffin    TestSuite suite = new TestSuite("Multimaps.filter*");
5580888a09821a98ac0680fad765217302858e70fa4Paul Duffin    suite.addTest(SetMultimapTestSuiteBuilder.using(new FilteredSetMultimapGenerator() {
5590888a09821a98ac0680fad765217302858e70fa4Paul Duffin        @Override
5600888a09821a98ac0680fad765217302858e70fa4Paul Duffin        SetMultimap<String, Integer> filter(SetMultimap<String, Integer> multimap) {
5610888a09821a98ac0680fad765217302858e70fa4Paul Duffin          multimap.put("foo", 17);
5620888a09821a98ac0680fad765217302858e70fa4Paul Duffin          multimap.put("bar", 32);
5630888a09821a98ac0680fad765217302858e70fa4Paul Duffin          multimap.put("foo", 16);
5640888a09821a98ac0680fad765217302858e70fa4Paul Duffin          return Multimaps.filterKeys(multimap,
5650888a09821a98ac0680fad765217302858e70fa4Paul Duffin              Predicates.not(Predicates.in(ImmutableSet.of("foo", "bar"))));
5660888a09821a98ac0680fad765217302858e70fa4Paul Duffin        }
5670888a09821a98ac0680fad765217302858e70fa4Paul Duffin      })
5680888a09821a98ac0680fad765217302858e70fa4Paul Duffin      .named("Multimaps.filterKeys[SetMultimap, Predicate]")
5690888a09821a98ac0680fad765217302858e70fa4Paul Duffin      .withFeatures(
5700888a09821a98ac0680fad765217302858e70fa4Paul Duffin          CollectionSize.ANY,
5710888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MultimapFeature.VALUE_COLLECTIONS_SUPPORT_ITERATOR_REMOVE,
5720888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.GENERAL_PURPOSE,
5730888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_NULL_KEYS,
5740888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_NULL_VALUES,
5750888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_ANY_NULL_QUERIES)
5760888a09821a98ac0680fad765217302858e70fa4Paul Duffin      .createTestSuite());
5770888a09821a98ac0680fad765217302858e70fa4Paul Duffin
5780888a09821a98ac0680fad765217302858e70fa4Paul Duffin    suite.addTest(ListMultimapTestSuiteBuilder.using(new FilteredListMultimapGenerator() {
5797dd252788645e940eada959bdde927426e2531c9Paul Duffin        @Override
5800888a09821a98ac0680fad765217302858e70fa4Paul Duffin        ListMultimap<String, Integer> filter(ListMultimap<String, Integer> multimap) {
5817dd252788645e940eada959bdde927426e2531c9Paul Duffin          multimap.put("foo", 17);
5827dd252788645e940eada959bdde927426e2531c9Paul Duffin          multimap.put("bar", 32);
5837dd252788645e940eada959bdde927426e2531c9Paul Duffin          multimap.put("foo", 16);
5847dd252788645e940eada959bdde927426e2531c9Paul Duffin          return Multimaps.filterKeys(multimap,
5857dd252788645e940eada959bdde927426e2531c9Paul Duffin              Predicates.not(Predicates.in(ImmutableSet.of("foo", "bar"))));
5867dd252788645e940eada959bdde927426e2531c9Paul Duffin        }
5877dd252788645e940eada959bdde927426e2531c9Paul Duffin      })
5880888a09821a98ac0680fad765217302858e70fa4Paul Duffin      .named("Multimaps.filterKeys[ListMultimap, Predicate]")
5890888a09821a98ac0680fad765217302858e70fa4Paul Duffin      .withFeatures(
5900888a09821a98ac0680fad765217302858e70fa4Paul Duffin          CollectionSize.ANY,
5910888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MultimapFeature.VALUE_COLLECTIONS_SUPPORT_ITERATOR_REMOVE,
5920888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.GENERAL_PURPOSE,
5930888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_NULL_KEYS,
5940888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_NULL_VALUES,
5950888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_ANY_NULL_QUERIES)
5960888a09821a98ac0680fad765217302858e70fa4Paul Duffin      .createTestSuite());
5970888a09821a98ac0680fad765217302858e70fa4Paul Duffin    suite.addTest(ListMultimapTestSuiteBuilder.using(new FilteredListMultimapGenerator() {
5980888a09821a98ac0680fad765217302858e70fa4Paul Duffin        @Override
5990888a09821a98ac0680fad765217302858e70fa4Paul Duffin        ListMultimap<String, Integer> filter(ListMultimap<String, Integer> multimap) {
6000888a09821a98ac0680fad765217302858e70fa4Paul Duffin          multimap.put("foo", 17);
6010888a09821a98ac0680fad765217302858e70fa4Paul Duffin          multimap.put("bar", 32);
6020888a09821a98ac0680fad765217302858e70fa4Paul Duffin          multimap.put("foo", 16);
6030888a09821a98ac0680fad765217302858e70fa4Paul Duffin          multimap = Multimaps.filterKeys(multimap, Predicates.not(Predicates.equalTo("foo")));
6040888a09821a98ac0680fad765217302858e70fa4Paul Duffin          return Multimaps.filterKeys(multimap, Predicates.not(Predicates.equalTo("bar")));
6050888a09821a98ac0680fad765217302858e70fa4Paul Duffin        }
6060888a09821a98ac0680fad765217302858e70fa4Paul Duffin      })
6070888a09821a98ac0680fad765217302858e70fa4Paul Duffin      .named("Multimaps.filterKeys[Multimaps.filterKeys[ListMultimap], Predicate]")
6087dd252788645e940eada959bdde927426e2531c9Paul Duffin      .withFeatures(
6097dd252788645e940eada959bdde927426e2531c9Paul Duffin          CollectionSize.ANY,
6100888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MultimapFeature.VALUE_COLLECTIONS_SUPPORT_ITERATOR_REMOVE,
6117dd252788645e940eada959bdde927426e2531c9Paul Duffin          MapFeature.GENERAL_PURPOSE,
6127dd252788645e940eada959bdde927426e2531c9Paul Duffin          MapFeature.ALLOWS_NULL_KEYS,
6130888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_NULL_VALUES,
6140888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_ANY_NULL_QUERIES)
6157dd252788645e940eada959bdde927426e2531c9Paul Duffin      .createTestSuite());
6160888a09821a98ac0680fad765217302858e70fa4Paul Duffin    suite.addTest(SetMultimapTestSuiteBuilder.using(new FilteredSetMultimapGenerator() {
6177dd252788645e940eada959bdde927426e2531c9Paul Duffin        @Override
6180888a09821a98ac0680fad765217302858e70fa4Paul Duffin        SetMultimap<String, Integer> filter(SetMultimap<String, Integer> multimap) {
6197dd252788645e940eada959bdde927426e2531c9Paul Duffin          multimap.put("one", 314);
6207dd252788645e940eada959bdde927426e2531c9Paul Duffin          multimap.put("two", 159);
6217dd252788645e940eada959bdde927426e2531c9Paul Duffin          multimap.put("one", 265);
6227dd252788645e940eada959bdde927426e2531c9Paul Duffin          return Multimaps.filterValues(multimap,
6237dd252788645e940eada959bdde927426e2531c9Paul Duffin              Predicates.not(Predicates.in(ImmutableSet.of(314, 159, 265))));
6247dd252788645e940eada959bdde927426e2531c9Paul Duffin        }
6257dd252788645e940eada959bdde927426e2531c9Paul Duffin      })
6260888a09821a98ac0680fad765217302858e70fa4Paul Duffin      .named("Multimaps.filterValues[SetMultimap, Predicate]")
6277dd252788645e940eada959bdde927426e2531c9Paul Duffin      .withFeatures(
6287dd252788645e940eada959bdde927426e2531c9Paul Duffin          CollectionSize.ANY,
6297dd252788645e940eada959bdde927426e2531c9Paul Duffin          MapFeature.GENERAL_PURPOSE,
6307dd252788645e940eada959bdde927426e2531c9Paul Duffin          MapFeature.ALLOWS_NULL_KEYS,
6310888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_NULL_VALUES,
6320888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_ANY_NULL_QUERIES)
6337dd252788645e940eada959bdde927426e2531c9Paul Duffin      .createTestSuite());
6340888a09821a98ac0680fad765217302858e70fa4Paul Duffin    suite.addTest(SetMultimapTestSuiteBuilder.using(new FilteredSetMultimapGenerator() {
6357dd252788645e940eada959bdde927426e2531c9Paul Duffin        @Override
6360888a09821a98ac0680fad765217302858e70fa4Paul Duffin        SetMultimap<String, Integer> filter(SetMultimap<String, Integer> multimap) {
6377dd252788645e940eada959bdde927426e2531c9Paul Duffin          ImmutableSetMultimap<String, Integer> badEntries =
6387dd252788645e940eada959bdde927426e2531c9Paul Duffin              ImmutableSetMultimap.of("foo", 314, "one", 159, "two", 265, "bar", 358);
6397dd252788645e940eada959bdde927426e2531c9Paul Duffin          multimap.putAll(badEntries);
6407dd252788645e940eada959bdde927426e2531c9Paul Duffin          return Multimaps.filterEntries(multimap,
6417dd252788645e940eada959bdde927426e2531c9Paul Duffin              Predicates.not(Predicates.in(badEntries.entries())));
6427dd252788645e940eada959bdde927426e2531c9Paul Duffin        }
6437dd252788645e940eada959bdde927426e2531c9Paul Duffin      })
6440888a09821a98ac0680fad765217302858e70fa4Paul Duffin      .named("Multimaps.filterEntries[SetMultimap, Predicate]")
6457dd252788645e940eada959bdde927426e2531c9Paul Duffin      .withFeatures(
6467dd252788645e940eada959bdde927426e2531c9Paul Duffin          CollectionSize.ANY,
6477dd252788645e940eada959bdde927426e2531c9Paul Duffin          MapFeature.GENERAL_PURPOSE,
6487dd252788645e940eada959bdde927426e2531c9Paul Duffin          MapFeature.ALLOWS_NULL_KEYS,
6490888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_NULL_VALUES,
6500888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_ANY_NULL_QUERIES)
6517dd252788645e940eada959bdde927426e2531c9Paul Duffin      .createTestSuite());
6520888a09821a98ac0680fad765217302858e70fa4Paul Duffin    suite.addTest(SetMultimapTestSuiteBuilder.using(new FilteredSetMultimapGenerator() {
6537dd252788645e940eada959bdde927426e2531c9Paul Duffin        @Override
6540888a09821a98ac0680fad765217302858e70fa4Paul Duffin        SetMultimap<String, Integer> filter(SetMultimap<String, Integer> multimap) {
6557dd252788645e940eada959bdde927426e2531c9Paul Duffin          ImmutableSetMultimap<String, Integer> badEntries =
6567dd252788645e940eada959bdde927426e2531c9Paul Duffin              ImmutableSetMultimap.of("foo", 314, "one", 159, "two", 265, "bar", 358);
6577dd252788645e940eada959bdde927426e2531c9Paul Duffin          multimap.putAll(badEntries);
6587dd252788645e940eada959bdde927426e2531c9Paul Duffin          multimap = Multimaps.filterKeys(multimap,
6597dd252788645e940eada959bdde927426e2531c9Paul Duffin              Predicates.not(Predicates.in(ImmutableSet.of("foo", "bar"))));
6607dd252788645e940eada959bdde927426e2531c9Paul Duffin          return Multimaps.filterEntries(multimap,
6617dd252788645e940eada959bdde927426e2531c9Paul Duffin              Predicates.not(Predicates.in(badEntries.entries())));
6627dd252788645e940eada959bdde927426e2531c9Paul Duffin        }
6637dd252788645e940eada959bdde927426e2531c9Paul Duffin      })
6640888a09821a98ac0680fad765217302858e70fa4Paul Duffin      .named("Multimaps.filterEntries[Multimaps.filterKeys[SetMultimap]]")
6657dd252788645e940eada959bdde927426e2531c9Paul Duffin      .withFeatures(
6667dd252788645e940eada959bdde927426e2531c9Paul Duffin          CollectionSize.ANY,
6677dd252788645e940eada959bdde927426e2531c9Paul Duffin          MapFeature.GENERAL_PURPOSE,
6687dd252788645e940eada959bdde927426e2531c9Paul Duffin          MapFeature.ALLOWS_NULL_KEYS,
6690888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_NULL_VALUES,
6700888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_ANY_NULL_QUERIES)
6717dd252788645e940eada959bdde927426e2531c9Paul Duffin      .createTestSuite());
6720888a09821a98ac0680fad765217302858e70fa4Paul Duffin    suite.addTest(SetMultimapTestSuiteBuilder.using(new FilteredSetMultimapGenerator() {
6737dd252788645e940eada959bdde927426e2531c9Paul Duffin        @Override
6740888a09821a98ac0680fad765217302858e70fa4Paul Duffin        SetMultimap<String, Integer> filter(SetMultimap<String, Integer> multimap) {
6757dd252788645e940eada959bdde927426e2531c9Paul Duffin          ImmutableSetMultimap<String, Integer> badEntries =
6767dd252788645e940eada959bdde927426e2531c9Paul Duffin              ImmutableSetMultimap.of("foo", 314, "one", 159, "two", 265, "bar", 358);
6777dd252788645e940eada959bdde927426e2531c9Paul Duffin          multimap.putAll(badEntries);
6787dd252788645e940eada959bdde927426e2531c9Paul Duffin          multimap = Multimaps.filterEntries(multimap,
6797dd252788645e940eada959bdde927426e2531c9Paul Duffin              Predicates.not(Predicates.in(ImmutableMap.of("one", 159, "two", 265).entrySet())));
6807dd252788645e940eada959bdde927426e2531c9Paul Duffin          return Multimaps.filterKeys(multimap,
6817dd252788645e940eada959bdde927426e2531c9Paul Duffin              Predicates.not(Predicates.in(ImmutableSet.of("foo", "bar"))));
6827dd252788645e940eada959bdde927426e2531c9Paul Duffin        }
6837dd252788645e940eada959bdde927426e2531c9Paul Duffin      })
6840888a09821a98ac0680fad765217302858e70fa4Paul Duffin      .named("Multimaps.filterKeys[Multimaps.filterEntries[SetMultimap]]")
6857dd252788645e940eada959bdde927426e2531c9Paul Duffin      .withFeatures(
6867dd252788645e940eada959bdde927426e2531c9Paul Duffin          CollectionSize.ANY,
6877dd252788645e940eada959bdde927426e2531c9Paul Duffin          MapFeature.GENERAL_PURPOSE,
6887dd252788645e940eada959bdde927426e2531c9Paul Duffin          MapFeature.ALLOWS_NULL_KEYS,
6890888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_NULL_VALUES,
6900888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_ANY_NULL_QUERIES)
6917dd252788645e940eada959bdde927426e2531c9Paul Duffin      .createTestSuite());
6920888a09821a98ac0680fad765217302858e70fa4Paul Duffin    suite.addTest(SetMultimapTestSuiteBuilder.using(new FilteredSetMultimapGenerator() {
6937dd252788645e940eada959bdde927426e2531c9Paul Duffin        @Override
6940888a09821a98ac0680fad765217302858e70fa4Paul Duffin        SetMultimap<String, Integer> filter(SetMultimap<String, Integer> multimap) {
6957dd252788645e940eada959bdde927426e2531c9Paul Duffin          ImmutableSetMultimap<String, Integer> badEntries =
6967dd252788645e940eada959bdde927426e2531c9Paul Duffin              ImmutableSetMultimap.of("foo", 314, "bar", 358);
6977dd252788645e940eada959bdde927426e2531c9Paul Duffin          multimap.putAll(badEntries);
6987dd252788645e940eada959bdde927426e2531c9Paul Duffin          multimap = Multimaps.filterKeys(multimap, Predicates.not(Predicates.equalTo("foo")));
6997dd252788645e940eada959bdde927426e2531c9Paul Duffin          multimap = Multimaps.filterKeys(multimap, Predicates.not(Predicates.equalTo("bar")));
7007dd252788645e940eada959bdde927426e2531c9Paul Duffin          return multimap;
7017dd252788645e940eada959bdde927426e2531c9Paul Duffin        }
7027dd252788645e940eada959bdde927426e2531c9Paul Duffin      })
7030888a09821a98ac0680fad765217302858e70fa4Paul Duffin      .named("Multimaps.filterKeys[Multimaps.filterKeys[SetMultimap]]")
7047dd252788645e940eada959bdde927426e2531c9Paul Duffin      .withFeatures(
7057dd252788645e940eada959bdde927426e2531c9Paul Duffin          CollectionSize.ANY,
7060888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MultimapFeature.VALUE_COLLECTIONS_SUPPORT_ITERATOR_REMOVE,
7077dd252788645e940eada959bdde927426e2531c9Paul Duffin          MapFeature.GENERAL_PURPOSE,
7087dd252788645e940eada959bdde927426e2531c9Paul Duffin          MapFeature.ALLOWS_NULL_KEYS,
7090888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_NULL_VALUES,
7100888a09821a98ac0680fad765217302858e70fa4Paul Duffin          MapFeature.ALLOWS_ANY_NULL_QUERIES)
7117dd252788645e940eada959bdde927426e2531c9Paul Duffin      .createTestSuite());
7127dd252788645e940eada959bdde927426e2531c9Paul Duffin    return suite;
7137dd252788645e940eada959bdde927426e2531c9Paul Duffin  }
7147dd252788645e940eada959bdde927426e2531c9Paul Duffin}
715