11d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert/*
21d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert * Copyright (C) 2007 The Guava Authors
31d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert *
41d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert * Licensed under the Apache License, Version 2.0 (the "License");
51d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert * you may not use this file except in compliance with the License.
61d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert * You may obtain a copy of the License at
71d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert *
81d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert * http://www.apache.org/licenses/LICENSE-2.0
91d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert *
101d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert * Unless required by applicable law or agreed to in writing, software
111d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert * distributed under the License is distributed on an "AS IS" BASIS,
121d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
131d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert * See the License for the specific language governing permissions and
141d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert * limitations under the License.
151d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert */
161d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
171d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertpackage com.google.common.collect;
181d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
191d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport static com.google.common.base.Preconditions.checkNotNull;
200888a09821a98ac0680fad765217302858e70fa4Paul Duffinimport static com.google.common.collect.CollectPreconditions.checkNonnegative;
210888a09821a98ac0680fad765217302858e70fa4Paul Duffinimport static com.google.common.collect.CollectPreconditions.checkRemove;
221d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
230888a09821a98ac0680fad765217302858e70fa4Paul Duffinimport com.google.common.annotations.Beta;
241d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport com.google.common.annotations.GwtCompatible;
251d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport com.google.common.annotations.GwtIncompatible;
261d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport com.google.common.base.Function;
271d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport com.google.common.base.Predicate;
281d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport com.google.common.base.Predicates;
291d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport com.google.common.base.Supplier;
301d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport com.google.common.collect.Maps.EntryTransformer;
311d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
321d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport java.io.IOException;
331d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport java.io.ObjectInputStream;
341d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport java.io.ObjectOutputStream;
351d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport java.io.Serializable;
361d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport java.util.AbstractCollection;
371d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport java.util.Collection;
381d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport java.util.Collections;
391d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport java.util.Comparator;
401d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport java.util.HashSet;
411d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport java.util.Iterator;
421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport java.util.List;
431d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport java.util.Map;
441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport java.util.Map.Entry;
451d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport java.util.NoSuchElementException;
461d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport java.util.Set;
471d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport java.util.SortedSet;
481d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
491d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertimport javax.annotation.Nullable;
501d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
511d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert/**
521d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert * Provides static methods acting on or generating a {@code Multimap}.
531d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert *
547dd252788645e940eada959bdde927426e2531c9Paul Duffin * <p>See the Guava User Guide article on <a href=
557dd252788645e940eada959bdde927426e2531c9Paul Duffin * "http://code.google.com/p/guava-libraries/wiki/CollectionUtilitiesExplained#Multimaps">
567dd252788645e940eada959bdde927426e2531c9Paul Duffin * {@code Multimaps}</a>.
577dd252788645e940eada959bdde927426e2531c9Paul Duffin *
581d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert * @author Jared Levy
591d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert * @author Robert Konigsberg
601d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert * @author Mike Bostock
611d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert * @author Louis Wasserman
621d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert * @since 2.0 (imported from Google Collections Library)
631d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert */
641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert@GwtCompatible(emulated = true)
651d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringertpublic final class Multimaps {
661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  private Multimaps() {}
671d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
681d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
697dd252788645e940eada959bdde927426e2531c9Paul Duffin   * Creates a new {@code Multimap} backed by {@code map}, whose internal value
707dd252788645e940eada959bdde927426e2531c9Paul Duffin   * collections are generated by {@code factory}.
717dd252788645e940eada959bdde927426e2531c9Paul Duffin   *
727dd252788645e940eada959bdde927426e2531c9Paul Duffin   * <b>Warning: do not use</b> this method when the collections returned by
737dd252788645e940eada959bdde927426e2531c9Paul Duffin   * {@code factory} implement either {@link List} or {@code Set}! Use the more
747dd252788645e940eada959bdde927426e2531c9Paul Duffin   * specific method {@link #newListMultimap}, {@link #newSetMultimap} or {@link
757dd252788645e940eada959bdde927426e2531c9Paul Duffin   * #newSortedSetMultimap} instead, to avoid very surprising behavior from
767dd252788645e940eada959bdde927426e2531c9Paul Duffin   * {@link Multimap#equals}.
771d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
781d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The {@code factory}-generated and {@code map} classes determine the
791d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap iteration order. They also specify the behavior of the
801d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code equals}, {@code hashCode}, and {@code toString} methods for the
811d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap and its returned views. However, the multimap's {@code get}
821d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * method returns instances of a different class than {@code factory.get()}
831d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * does.
841d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
851d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The multimap is serializable if {@code map}, {@code factory}, the
861d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * collections generated by {@code factory}, and the multimap contents are all
871d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * serializable.
881d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
891d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The multimap is not threadsafe when any concurrent operations update the
901d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap, even if {@code map} and the instances generated by
911d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code factory} are. Concurrent read operations will work correctly. To
921d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * allow concurrent update operations, wrap the multimap with a call to
931d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link #synchronizedMultimap}.
941d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
951d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Call this method only when the simpler methods
961d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link ArrayListMultimap#create()}, {@link HashMultimap#create()},
971d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link LinkedHashMultimap#create()}, {@link LinkedListMultimap#create()},
981d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link TreeMultimap#create()}, and
991d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link TreeMultimap#create(Comparator, Comparator)} won't suffice.
1001d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
1011d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Note: the multimap assumes complete ownership over of {@code map} and
1021d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * the collections returned by {@code factory}. Those objects should not be
1031d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * manually updated and they should not use soft, weak, or phantom references.
1041d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
1051d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param map place to store the mapping from each key to its corresponding
1061d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     values
1071d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param factory supplier of new, empty collections that will each hold all
1081d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     values for a given key
1091d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @throws IllegalArgumentException if {@code map} is not empty
1101d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
1111d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  public static <K, V> Multimap<K, V> newMultimap(Map<K, Collection<V>> map,
1121d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      final Supplier<? extends Collection<V>> factory) {
1131d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return new CustomMultimap<K, V>(map, factory);
1141d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
1151d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
1167dd252788645e940eada959bdde927426e2531c9Paul Duffin  private static class CustomMultimap<K, V> extends AbstractMapBasedMultimap<K, V> {
1171d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    transient Supplier<? extends Collection<V>> factory;
1181d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
1190888a09821a98ac0680fad765217302858e70fa4Paul Duffin    CustomMultimap(Map<K, Collection<V>> map,
1200888a09821a98ac0680fad765217302858e70fa4Paul Duffin        Supplier<? extends Collection<V>> factory) {
1211d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      super(map);
1221d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      this.factory = checkNotNull(factory);
1231d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
1241d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
1250888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override protected Collection<V> createCollection() {
1261d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return factory.get();
1271d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
1281d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
1291d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    // can't use Serialization writeMultimap and populateMultimap methods since
1301d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    // there's no way to generate the empty backing map.
1311d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
1321d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    /** @serialData the factory and the backing map */
1331d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @GwtIncompatible("java.io.ObjectOutputStream")
1341d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    private void writeObject(ObjectOutputStream stream) throws IOException {
1351d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      stream.defaultWriteObject();
1361d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      stream.writeObject(factory);
1371d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      stream.writeObject(backingMap());
1381d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
1391d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
1401d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @GwtIncompatible("java.io.ObjectInputStream")
1410888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @SuppressWarnings("unchecked") // reading data stored by writeObject
1420888a09821a98ac0680fad765217302858e70fa4Paul Duffin    private void readObject(ObjectInputStream stream)
1430888a09821a98ac0680fad765217302858e70fa4Paul Duffin        throws IOException, ClassNotFoundException {
1441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      stream.defaultReadObject();
1451d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      factory = (Supplier<? extends Collection<V>>) stream.readObject();
1461d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      Map<K, Collection<V>> map = (Map<K, Collection<V>>) stream.readObject();
1471d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      setMap(map);
1481d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
1491d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
1501d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @GwtIncompatible("java serialization not supported")
1511d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    private static final long serialVersionUID = 0;
1521d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
1531d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
1541d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
1551d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Creates a new {@code ListMultimap} that uses the provided map and factory.
1561d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * It can generate a multimap based on arbitrary {@link Map} and {@link List}
1571d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * classes.
1581d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
1591d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The {@code factory}-generated and {@code map} classes determine the
1601d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap iteration order. They also specify the behavior of the
1611d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code equals}, {@code hashCode}, and {@code toString} methods for the
1621d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap and its returned views. The multimap's {@code get}, {@code
1631d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * removeAll}, and {@code replaceValues} methods return {@code RandomAccess}
1641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * lists if the factory does. However, the multimap's {@code get} method
1651d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * returns instances of a different class than does {@code factory.get()}.
1661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
1671d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The multimap is serializable if {@code map}, {@code factory}, the
1681d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * lists generated by {@code factory}, and the multimap contents are all
1691d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * serializable.
1701d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
1711d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The multimap is not threadsafe when any concurrent operations update the
1721d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap, even if {@code map} and the instances generated by
1731d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code factory} are. Concurrent read operations will work correctly. To
1741d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * allow concurrent update operations, wrap the multimap with a call to
1751d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link #synchronizedListMultimap}.
1761d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
1771d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Call this method only when the simpler methods
1781d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link ArrayListMultimap#create()} and {@link LinkedListMultimap#create()}
1791d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * won't suffice.
1801d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
1811d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Note: the multimap assumes complete ownership over of {@code map} and
1821d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * the lists returned by {@code factory}. Those objects should not be manually
1831d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * updated, they should be empty when provided, and they should not use soft,
1841d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * weak, or phantom references.
1851d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
1861d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param map place to store the mapping from each key to its corresponding
1871d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     values
1881d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param factory supplier of new, empty lists that will each hold all values
1891d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     for a given key
1901d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @throws IllegalArgumentException if {@code map} is not empty
1911d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
1920888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> ListMultimap<K, V> newListMultimap(
1930888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Map<K, Collection<V>> map, final Supplier<? extends List<V>> factory) {
1941d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return new CustomListMultimap<K, V>(map, factory);
1951d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
1961d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
1970888a09821a98ac0680fad765217302858e70fa4Paul Duffin  private static class CustomListMultimap<K, V>
1980888a09821a98ac0680fad765217302858e70fa4Paul Duffin      extends AbstractListMultimap<K, V> {
1991d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    transient Supplier<? extends List<V>> factory;
2001d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
2010888a09821a98ac0680fad765217302858e70fa4Paul Duffin    CustomListMultimap(Map<K, Collection<V>> map,
2020888a09821a98ac0680fad765217302858e70fa4Paul Duffin        Supplier<? extends List<V>> factory) {
2031d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      super(map);
2041d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      this.factory = checkNotNull(factory);
2051d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
2061d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
2070888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override protected List<V> createCollection() {
2081d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return factory.get();
2091d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
2101d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
2111d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    /** @serialData the factory and the backing map */
2121d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @GwtIncompatible("java.io.ObjectOutputStream")
2131d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    private void writeObject(ObjectOutputStream stream) throws IOException {
2141d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      stream.defaultWriteObject();
2151d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      stream.writeObject(factory);
2161d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      stream.writeObject(backingMap());
2171d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
2181d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
2191d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @GwtIncompatible("java.io.ObjectInputStream")
2200888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @SuppressWarnings("unchecked") // reading data stored by writeObject
2210888a09821a98ac0680fad765217302858e70fa4Paul Duffin    private void readObject(ObjectInputStream stream)
2220888a09821a98ac0680fad765217302858e70fa4Paul Duffin        throws IOException, ClassNotFoundException {
2231d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      stream.defaultReadObject();
2241d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      factory = (Supplier<? extends List<V>>) stream.readObject();
2251d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      Map<K, Collection<V>> map = (Map<K, Collection<V>>) stream.readObject();
2261d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      setMap(map);
2271d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
2281d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
2291d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @GwtIncompatible("java serialization not supported")
2301d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    private static final long serialVersionUID = 0;
2311d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
2321d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
2331d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
2341d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Creates a new {@code SetMultimap} that uses the provided map and factory.
2351d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * It can generate a multimap based on arbitrary {@link Map} and {@link Set}
2361d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * classes.
2371d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
2381d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The {@code factory}-generated and {@code map} classes determine the
2391d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap iteration order. They also specify the behavior of the
2401d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code equals}, {@code hashCode}, and {@code toString} methods for the
2411d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap and its returned views. However, the multimap's {@code get}
2421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * method returns instances of a different class than {@code factory.get()}
2431d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * does.
2441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
2451d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The multimap is serializable if {@code map}, {@code factory}, the
2461d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * sets generated by {@code factory}, and the multimap contents are all
2471d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * serializable.
2481d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
2491d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The multimap is not threadsafe when any concurrent operations update the
2501d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap, even if {@code map} and the instances generated by
2511d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code factory} are. Concurrent read operations will work correctly. To
2521d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * allow concurrent update operations, wrap the multimap with a call to
2531d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link #synchronizedSetMultimap}.
2541d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
2551d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Call this method only when the simpler methods
2561d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link HashMultimap#create()}, {@link LinkedHashMultimap#create()},
2571d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link TreeMultimap#create()}, and
2581d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link TreeMultimap#create(Comparator, Comparator)} won't suffice.
2591d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
2601d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Note: the multimap assumes complete ownership over of {@code map} and
2611d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * the sets returned by {@code factory}. Those objects should not be manually
2621d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * updated and they should not use soft, weak, or phantom references.
2631d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
2641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param map place to store the mapping from each key to its corresponding
2651d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     values
2661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param factory supplier of new, empty sets that will each hold all values
2671d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     for a given key
2681d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @throws IllegalArgumentException if {@code map} is not empty
2691d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
2700888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> SetMultimap<K, V> newSetMultimap(
2710888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Map<K, Collection<V>> map, final Supplier<? extends Set<V>> factory) {
2721d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return new CustomSetMultimap<K, V>(map, factory);
2731d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
2741d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
2750888a09821a98ac0680fad765217302858e70fa4Paul Duffin  private static class CustomSetMultimap<K, V>
2760888a09821a98ac0680fad765217302858e70fa4Paul Duffin      extends AbstractSetMultimap<K, V> {
2771d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    transient Supplier<? extends Set<V>> factory;
2781d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
2790888a09821a98ac0680fad765217302858e70fa4Paul Duffin    CustomSetMultimap(Map<K, Collection<V>> map,
2800888a09821a98ac0680fad765217302858e70fa4Paul Duffin        Supplier<? extends Set<V>> factory) {
2811d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      super(map);
2821d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      this.factory = checkNotNull(factory);
2831d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
2841d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
2850888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override protected Set<V> createCollection() {
2861d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return factory.get();
2871d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
2881d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
2891d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    /** @serialData the factory and the backing map */
2901d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @GwtIncompatible("java.io.ObjectOutputStream")
2911d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    private void writeObject(ObjectOutputStream stream) throws IOException {
2921d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      stream.defaultWriteObject();
2931d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      stream.writeObject(factory);
2941d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      stream.writeObject(backingMap());
2951d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
2961d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
2971d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @GwtIncompatible("java.io.ObjectInputStream")
2980888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @SuppressWarnings("unchecked") // reading data stored by writeObject
2990888a09821a98ac0680fad765217302858e70fa4Paul Duffin    private void readObject(ObjectInputStream stream)
3000888a09821a98ac0680fad765217302858e70fa4Paul Duffin        throws IOException, ClassNotFoundException {
3011d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      stream.defaultReadObject();
3021d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      factory = (Supplier<? extends Set<V>>) stream.readObject();
3031d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      Map<K, Collection<V>> map = (Map<K, Collection<V>>) stream.readObject();
3041d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      setMap(map);
3051d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
3061d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
3071d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @GwtIncompatible("not needed in emulated source")
3081d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    private static final long serialVersionUID = 0;
3091d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
3101d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
3111d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
3121d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Creates a new {@code SortedSetMultimap} that uses the provided map and
3131d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * factory. It can generate a multimap based on arbitrary {@link Map} and
3141d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link SortedSet} classes.
3151d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
3161d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The {@code factory}-generated and {@code map} classes determine the
3171d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap iteration order. They also specify the behavior of the
3181d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code equals}, {@code hashCode}, and {@code toString} methods for the
3191d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap and its returned views. However, the multimap's {@code get}
3201d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * method returns instances of a different class than {@code factory.get()}
3211d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * does.
3221d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
3231d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The multimap is serializable if {@code map}, {@code factory}, the
3241d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * sets generated by {@code factory}, and the multimap contents are all
3251d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * serializable.
3261d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
3271d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The multimap is not threadsafe when any concurrent operations update the
3281d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap, even if {@code map} and the instances generated by
3291d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code factory} are. Concurrent read operations will work correctly. To
3301d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * allow concurrent update operations, wrap the multimap with a call to
3311d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link #synchronizedSortedSetMultimap}.
3321d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
3331d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Call this method only when the simpler methods
3341d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link TreeMultimap#create()} and
3351d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link TreeMultimap#create(Comparator, Comparator)} won't suffice.
3361d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
3371d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Note: the multimap assumes complete ownership over of {@code map} and
3381d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * the sets returned by {@code factory}. Those objects should not be manually
3391d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * updated and they should not use soft, weak, or phantom references.
3401d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
3411d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param map place to store the mapping from each key to its corresponding
3421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     values
3431d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param factory supplier of new, empty sorted sets that will each hold
3441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     all values for a given key
3451d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @throws IllegalArgumentException if {@code map} is not empty
3461d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
3470888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> SortedSetMultimap<K, V> newSortedSetMultimap(
3480888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Map<K, Collection<V>> map,
3491d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      final Supplier<? extends SortedSet<V>> factory) {
3501d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return new CustomSortedSetMultimap<K, V>(map, factory);
3511d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
3521d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
3530888a09821a98ac0680fad765217302858e70fa4Paul Duffin  private static class CustomSortedSetMultimap<K, V>
3540888a09821a98ac0680fad765217302858e70fa4Paul Duffin      extends AbstractSortedSetMultimap<K, V> {
3551d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    transient Supplier<? extends SortedSet<V>> factory;
3561d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    transient Comparator<? super V> valueComparator;
3571d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
3580888a09821a98ac0680fad765217302858e70fa4Paul Duffin    CustomSortedSetMultimap(Map<K, Collection<V>> map,
3590888a09821a98ac0680fad765217302858e70fa4Paul Duffin        Supplier<? extends SortedSet<V>> factory) {
3601d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      super(map);
3611d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      this.factory = checkNotNull(factory);
3621d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      valueComparator = factory.get().comparator();
3631d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
3641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
3650888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override protected SortedSet<V> createCollection() {
3661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return factory.get();
3671d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
3681d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
3690888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Comparator<? super V> valueComparator() {
3701d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return valueComparator;
3711d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
3721d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
3731d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    /** @serialData the factory and the backing map */
3741d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @GwtIncompatible("java.io.ObjectOutputStream")
3751d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    private void writeObject(ObjectOutputStream stream) throws IOException {
3761d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      stream.defaultWriteObject();
3771d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      stream.writeObject(factory);
3781d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      stream.writeObject(backingMap());
3791d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
3801d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
3811d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @GwtIncompatible("java.io.ObjectInputStream")
3820888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @SuppressWarnings("unchecked") // reading data stored by writeObject
3830888a09821a98ac0680fad765217302858e70fa4Paul Duffin    private void readObject(ObjectInputStream stream)
3840888a09821a98ac0680fad765217302858e70fa4Paul Duffin        throws IOException, ClassNotFoundException {
3851d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      stream.defaultReadObject();
3861d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      factory = (Supplier<? extends SortedSet<V>>) stream.readObject();
3871d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      valueComparator = factory.get().comparator();
3881d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      Map<K, Collection<V>> map = (Map<K, Collection<V>>) stream.readObject();
3891d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      setMap(map);
3901d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
3911d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
3921d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @GwtIncompatible("not needed in emulated source")
3931d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    private static final long serialVersionUID = 0;
3941d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
3951d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
3961d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
3971d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Copies each key-value mapping in {@code source} into {@code dest}, with
3981d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * its key and value reversed.
3991d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
4001d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>If {@code source} is an {@link ImmutableMultimap}, consider using
4011d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link ImmutableMultimap#inverse} instead.
4021d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
4031d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param source any multimap
4041d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param dest the multimap to copy into; usually empty
4051d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @return {@code dest}
4061d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
4071d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  public static <K, V, M extends Multimap<K, V>> M invertFrom(
4081d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      Multimap<? extends V, ? extends K> source, M dest) {
4091d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    checkNotNull(dest);
4101d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    for (Map.Entry<? extends V, ? extends K> entry : source.entries()) {
4111d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      dest.put(entry.getValue(), entry.getKey());
4121d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
4131d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return dest;
4141d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
4151d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
4161d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
4171d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns a synchronized (thread-safe) multimap backed by the specified
4181d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap. In order to guarantee serial access, it is critical that
4191d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <b>all</b> access to the backing multimap is accomplished through the
4201d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * returned multimap.
4211d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
4221d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>It is imperative that the user manually synchronize on the returned
4231d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap when accessing any of its collection views: <pre>   {@code
4241d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
4257dd252788645e940eada959bdde927426e2531c9Paul Duffin   *   Multimap<K, V> multimap = Multimaps.synchronizedMultimap(
4261d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       HashMultimap.<K, V>create());
4271d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   ...
4287dd252788645e940eada959bdde927426e2531c9Paul Duffin   *   Collection<V> values = multimap.get(key);  // Needn't be in synchronized block
4291d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   ...
4307dd252788645e940eada959bdde927426e2531c9Paul Duffin   *   synchronized (multimap) {  // Synchronizing on multimap, not values!
4317dd252788645e940eada959bdde927426e2531c9Paul Duffin   *     Iterator<V> i = values.iterator(); // Must be in synchronized block
4321d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     while (i.hasNext()) {
4331d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       foo(i.next());
4341d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     }
4351d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   }}</pre>
4361d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
4370888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>Failure to follow this advice may result in non-deterministic behavior.
4381d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
4391d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Note that the generated multimap's {@link Multimap#removeAll} and
4401d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link Multimap#replaceValues} methods return collections that aren't
4411d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * synchronized.
4421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
4431d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The returned multimap will be serializable if the specified multimap is
4441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * serializable.
4451d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
4461d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param multimap the multimap to be wrapped in a synchronized view
4471d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @return a synchronized view of the specified multimap
4481d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
4490888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> Multimap<K, V> synchronizedMultimap(
4500888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Multimap<K, V> multimap) {
4511d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return Synchronized.multimap(multimap, null);
4521d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
4531d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
4541d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
4551d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns an unmodifiable view of the specified multimap. Query operations on
4561d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * the returned multimap "read through" to the specified multimap, and
4571d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * attempts to modify the returned multimap, either directly or through the
4581d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap's views, result in an {@code UnsupportedOperationException}.
4591d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
4601d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Note that the generated multimap's {@link Multimap#removeAll} and
4611d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link Multimap#replaceValues} methods return collections that are
4621d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * modifiable.
4631d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
4641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The returned multimap will be serializable if the specified multimap is
4651d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * serializable.
4661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
4671d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param delegate the multimap for which an unmodifiable view is to be
4681d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     returned
4691d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @return an unmodifiable view of the specified multimap
4701d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
4710888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> Multimap<K, V> unmodifiableMultimap(
4720888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Multimap<K, V> delegate) {
4730888a09821a98ac0680fad765217302858e70fa4Paul Duffin    if (delegate instanceof UnmodifiableMultimap ||
4740888a09821a98ac0680fad765217302858e70fa4Paul Duffin        delegate instanceof ImmutableMultimap) {
4751d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return delegate;
4761d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
4771d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return new UnmodifiableMultimap<K, V>(delegate);
4781d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
4791d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
4801d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
4811d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Simply returns its argument.
4821d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
4831d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @deprecated no need to use this
4841d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @since 10.0
4851d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
4860888a09821a98ac0680fad765217302858e70fa4Paul Duffin  @Deprecated public static <K, V> Multimap<K, V> unmodifiableMultimap(
4870888a09821a98ac0680fad765217302858e70fa4Paul Duffin      ImmutableMultimap<K, V> delegate) {
4881d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return checkNotNull(delegate);
4891d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
4901d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
4910888a09821a98ac0680fad765217302858e70fa4Paul Duffin  private static class UnmodifiableMultimap<K, V>
4920888a09821a98ac0680fad765217302858e70fa4Paul Duffin      extends ForwardingMultimap<K, V> implements Serializable {
4931d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    final Multimap<K, V> delegate;
4941d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    transient Collection<Entry<K, V>> entries;
4951d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    transient Multiset<K> keys;
4961d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    transient Set<K> keySet;
4971d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    transient Collection<V> values;
4981d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    transient Map<K, Collection<V>> map;
4991d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
5001d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    UnmodifiableMultimap(final Multimap<K, V> delegate) {
5011d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      this.delegate = checkNotNull(delegate);
5021d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
5031d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
5040888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override protected Multimap<K, V> delegate() {
5051d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return delegate;
5061d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
5071d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
5080888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public void clear() {
5091d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
5101d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
5111d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
5120888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Map<K, Collection<V>> asMap() {
5131d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      Map<K, Collection<V>> result = map;
5141d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      if (result == null) {
5150888a09821a98ac0680fad765217302858e70fa4Paul Duffin        result = map = Collections.unmodifiableMap(
5160888a09821a98ac0680fad765217302858e70fa4Paul Duffin            Maps.transformValues(delegate.asMap(), new Function<Collection<V>, Collection<V>>() {
5170888a09821a98ac0680fad765217302858e70fa4Paul Duffin              @Override
5180888a09821a98ac0680fad765217302858e70fa4Paul Duffin              public Collection<V> apply(Collection<V> collection) {
5190888a09821a98ac0680fad765217302858e70fa4Paul Duffin                return unmodifiableValueCollection(collection);
5200888a09821a98ac0680fad765217302858e70fa4Paul Duffin              }
5210888a09821a98ac0680fad765217302858e70fa4Paul Duffin            }));
5221d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
5231d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return result;
5241d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
5251d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
5260888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Collection<Entry<K, V>> entries() {
5271d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      Collection<Entry<K, V>> result = entries;
5281d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      if (result == null) {
5291d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        entries = result = unmodifiableEntries(delegate.entries());
5301d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
5311d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return result;
5321d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
5331d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
5340888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Collection<V> get(K key) {
5351d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return unmodifiableValueCollection(delegate.get(key));
5361d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
5371d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
5380888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Multiset<K> keys() {
5391d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      Multiset<K> result = keys;
5401d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      if (result == null) {
5411d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        keys = result = Multisets.unmodifiableMultiset(delegate.keys());
5421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
5431d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return result;
5441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
5451d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
5460888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Set<K> keySet() {
5471d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      Set<K> result = keySet;
5481d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      if (result == null) {
5491d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        keySet = result = Collections.unmodifiableSet(delegate.keySet());
5501d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
5511d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return result;
5521d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
5531d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
5540888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public boolean put(K key, V value) {
5551d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
5561d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
5571d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
5580888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public boolean putAll(K key, Iterable<? extends V> values) {
5591d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
5601d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
5611d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
5621d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @Override
5631d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    public boolean putAll(Multimap<? extends K, ? extends V> multimap) {
5641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
5651d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
5661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
5670888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public boolean remove(Object key, Object value) {
5681d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
5691d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
5701d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
5710888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Collection<V> removeAll(Object key) {
5721d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
5731d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
5741d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
5750888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Collection<V> replaceValues(
5760888a09821a98ac0680fad765217302858e70fa4Paul Duffin        K key, Iterable<? extends V> values) {
5771d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
5781d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
5791d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
5800888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Collection<V> values() {
5811d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      Collection<V> result = values;
5821d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      if (result == null) {
5831d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        values = result = Collections.unmodifiableCollection(delegate.values());
5841d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
5851d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return result;
5861d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
5871d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
5881d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    private static final long serialVersionUID = 0;
5891d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
5901d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
5910888a09821a98ac0680fad765217302858e70fa4Paul Duffin  private static class UnmodifiableListMultimap<K, V>
5920888a09821a98ac0680fad765217302858e70fa4Paul Duffin      extends UnmodifiableMultimap<K, V> implements ListMultimap<K, V> {
5931d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    UnmodifiableListMultimap(ListMultimap<K, V> delegate) {
5941d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      super(delegate);
5951d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
5960888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public ListMultimap<K, V> delegate() {
5971d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return (ListMultimap<K, V>) super.delegate();
5981d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
5990888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public List<V> get(K key) {
6001d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return Collections.unmodifiableList(delegate().get(key));
6011d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
6020888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public List<V> removeAll(Object key) {
6031d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
6041d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
6050888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public List<V> replaceValues(
6060888a09821a98ac0680fad765217302858e70fa4Paul Duffin        K key, Iterable<? extends V> values) {
6071d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
6081d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
6091d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    private static final long serialVersionUID = 0;
6101d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
6111d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
6120888a09821a98ac0680fad765217302858e70fa4Paul Duffin  private static class UnmodifiableSetMultimap<K, V>
6130888a09821a98ac0680fad765217302858e70fa4Paul Duffin      extends UnmodifiableMultimap<K, V> implements SetMultimap<K, V> {
6141d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    UnmodifiableSetMultimap(SetMultimap<K, V> delegate) {
6151d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      super(delegate);
6161d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
6170888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public SetMultimap<K, V> delegate() {
6181d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return (SetMultimap<K, V>) super.delegate();
6191d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
6200888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Set<V> get(K key) {
6211d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      /*
6221d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert       * Note that this doesn't return a SortedSet when delegate is a
6231d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert       * SortedSetMultiset, unlike (SortedSet<V>) super.get().
6241d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert       */
6251d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return Collections.unmodifiableSet(delegate().get(key));
6261d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
6270888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Set<Map.Entry<K, V>> entries() {
6281d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return Maps.unmodifiableEntrySet(delegate().entries());
6291d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
6300888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Set<V> removeAll(Object key) {
6311d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
6321d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
6330888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Set<V> replaceValues(
6340888a09821a98ac0680fad765217302858e70fa4Paul Duffin        K key, Iterable<? extends V> values) {
6351d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
6361d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
6371d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    private static final long serialVersionUID = 0;
6381d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
6391d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
6400888a09821a98ac0680fad765217302858e70fa4Paul Duffin  private static class UnmodifiableSortedSetMultimap<K, V>
6410888a09821a98ac0680fad765217302858e70fa4Paul Duffin      extends UnmodifiableSetMultimap<K, V> implements SortedSetMultimap<K, V> {
6421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    UnmodifiableSortedSetMultimap(SortedSetMultimap<K, V> delegate) {
6431d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      super(delegate);
6441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
6450888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public SortedSetMultimap<K, V> delegate() {
6461d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return (SortedSetMultimap<K, V>) super.delegate();
6471d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
6480888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public SortedSet<V> get(K key) {
6491d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return Collections.unmodifiableSortedSet(delegate().get(key));
6501d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
6510888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public SortedSet<V> removeAll(Object key) {
6521d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
6531d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
6540888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public SortedSet<V> replaceValues(
6550888a09821a98ac0680fad765217302858e70fa4Paul Duffin        K key, Iterable<? extends V> values) {
6561d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
6571d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
6580888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
6591d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    public Comparator<? super V> valueComparator() {
6601d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return delegate().valueComparator();
6611d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
6621d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    private static final long serialVersionUID = 0;
6631d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
6641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
6651d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
6661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns a synchronized (thread-safe) {@code SetMultimap} backed by the
6671d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * specified multimap.
6681d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
6691d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>You must follow the warnings described in {@link #synchronizedMultimap}.
6701d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
6711d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The returned multimap will be serializable if the specified multimap is
6721d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * serializable.
6731d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
6741d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param multimap the multimap to be wrapped
6751d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @return a synchronized view of the specified multimap
6761d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
6770888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> SetMultimap<K, V> synchronizedSetMultimap(
6780888a09821a98ac0680fad765217302858e70fa4Paul Duffin      SetMultimap<K, V> multimap) {
6791d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return Synchronized.setMultimap(multimap, null);
6801d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
6811d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
6821d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
6831d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns an unmodifiable view of the specified {@code SetMultimap}. Query
6841d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * operations on the returned multimap "read through" to the specified
6851d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap, and attempts to modify the returned multimap, either directly or
6861d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * through the multimap's views, result in an
6871d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code UnsupportedOperationException}.
6881d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
6891d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Note that the generated multimap's {@link Multimap#removeAll} and
6901d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link Multimap#replaceValues} methods return collections that are
6911d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * modifiable.
6921d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
6931d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The returned multimap will be serializable if the specified multimap is
6941d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * serializable.
6951d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
6961d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param delegate the multimap for which an unmodifiable view is to be
6971d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     returned
6981d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @return an unmodifiable view of the specified multimap
6991d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
7000888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> SetMultimap<K, V> unmodifiableSetMultimap(
7010888a09821a98ac0680fad765217302858e70fa4Paul Duffin      SetMultimap<K, V> delegate) {
7020888a09821a98ac0680fad765217302858e70fa4Paul Duffin    if (delegate instanceof UnmodifiableSetMultimap ||
7030888a09821a98ac0680fad765217302858e70fa4Paul Duffin        delegate instanceof ImmutableSetMultimap) {
7041d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return delegate;
7051d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
7061d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return new UnmodifiableSetMultimap<K, V>(delegate);
7071d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
7081d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
7091d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
7101d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Simply returns its argument.
7111d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
7121d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @deprecated no need to use this
7131d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @since 10.0
7141d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
7150888a09821a98ac0680fad765217302858e70fa4Paul Duffin  @Deprecated public static <K, V> SetMultimap<K, V> unmodifiableSetMultimap(
7160888a09821a98ac0680fad765217302858e70fa4Paul Duffin      ImmutableSetMultimap<K, V> delegate) {
7171d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return checkNotNull(delegate);
7181d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
7191d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
7201d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
7211d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns a synchronized (thread-safe) {@code SortedSetMultimap} backed by
7221d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * the specified multimap.
7231d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
7241d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>You must follow the warnings described in {@link #synchronizedMultimap}.
7251d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
7261d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The returned multimap will be serializable if the specified multimap is
7271d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * serializable.
7281d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
7291d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param multimap the multimap to be wrapped
7301d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @return a synchronized view of the specified multimap
7311d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
7320888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> SortedSetMultimap<K, V>
7330888a09821a98ac0680fad765217302858e70fa4Paul Duffin      synchronizedSortedSetMultimap(SortedSetMultimap<K, V> multimap) {
7341d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return Synchronized.sortedSetMultimap(multimap, null);
7351d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
7361d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
7371d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
7381d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns an unmodifiable view of the specified {@code SortedSetMultimap}.
7391d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Query operations on the returned multimap "read through" to the specified
7401d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap, and attempts to modify the returned multimap, either directly or
7411d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * through the multimap's views, result in an
7421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code UnsupportedOperationException}.
7431d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
7441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Note that the generated multimap's {@link Multimap#removeAll} and
7451d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link Multimap#replaceValues} methods return collections that are
7461d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * modifiable.
7471d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
7481d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The returned multimap will be serializable if the specified multimap is
7491d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * serializable.
7501d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
7511d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param delegate the multimap for which an unmodifiable view is to be
7521d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     returned
7531d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @return an unmodifiable view of the specified multimap
7541d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
7551d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  public static <K, V> SortedSetMultimap<K, V> unmodifiableSortedSetMultimap(
7561d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      SortedSetMultimap<K, V> delegate) {
7571d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    if (delegate instanceof UnmodifiableSortedSetMultimap) {
7581d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return delegate;
7591d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
7601d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return new UnmodifiableSortedSetMultimap<K, V>(delegate);
7611d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
7621d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
7631d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
7641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns a synchronized (thread-safe) {@code ListMultimap} backed by the
7651d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * specified multimap.
7661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
7671d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>You must follow the warnings described in {@link #synchronizedMultimap}.
7681d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
7691d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param multimap the multimap to be wrapped
7701d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @return a synchronized view of the specified multimap
7711d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
7720888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> ListMultimap<K, V> synchronizedListMultimap(
7730888a09821a98ac0680fad765217302858e70fa4Paul Duffin      ListMultimap<K, V> multimap) {
7741d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return Synchronized.listMultimap(multimap, null);
7751d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
7761d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
7771d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
7781d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns an unmodifiable view of the specified {@code ListMultimap}. Query
7791d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * operations on the returned multimap "read through" to the specified
7801d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap, and attempts to modify the returned multimap, either directly or
7811d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * through the multimap's views, result in an
7821d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code UnsupportedOperationException}.
7831d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
7841d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Note that the generated multimap's {@link Multimap#removeAll} and
7851d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link Multimap#replaceValues} methods return collections that are
7861d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * modifiable.
7871d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
7881d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The returned multimap will be serializable if the specified multimap is
7891d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * serializable.
7901d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
7911d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param delegate the multimap for which an unmodifiable view is to be
7921d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     returned
7931d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @return an unmodifiable view of the specified multimap
7941d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
7950888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> ListMultimap<K, V> unmodifiableListMultimap(
7960888a09821a98ac0680fad765217302858e70fa4Paul Duffin      ListMultimap<K, V> delegate) {
7970888a09821a98ac0680fad765217302858e70fa4Paul Duffin    if (delegate instanceof UnmodifiableListMultimap ||
7980888a09821a98ac0680fad765217302858e70fa4Paul Duffin        delegate instanceof ImmutableListMultimap) {
7991d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return delegate;
8001d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
8011d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return new UnmodifiableListMultimap<K, V>(delegate);
8021d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
8031d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
8041d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
8051d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Simply returns its argument.
8061d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
8071d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @deprecated no need to use this
8081d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @since 10.0
8091d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
8100888a09821a98ac0680fad765217302858e70fa4Paul Duffin  @Deprecated public static <K, V> ListMultimap<K, V> unmodifiableListMultimap(
8111d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      ImmutableListMultimap<K, V> delegate) {
8121d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return checkNotNull(delegate);
8131d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
8141d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
8151d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
8161d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns an unmodifiable view of the specified collection, preserving the
8171d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * interface for instances of {@code SortedSet}, {@code Set}, {@code List} and
8181d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code Collection}, in that order of preference.
8191d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
8201d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param collection the collection for which to return an unmodifiable view
8211d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @return an unmodifiable view of the collection
8221d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
8230888a09821a98ac0680fad765217302858e70fa4Paul Duffin  private static <V> Collection<V> unmodifiableValueCollection(
8240888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Collection<V> collection) {
8251d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    if (collection instanceof SortedSet) {
8261d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return Collections.unmodifiableSortedSet((SortedSet<V>) collection);
8271d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    } else if (collection instanceof Set) {
8281d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return Collections.unmodifiableSet((Set<V>) collection);
8291d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    } else if (collection instanceof List) {
8301d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return Collections.unmodifiableList((List<V>) collection);
8311d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
8321d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return Collections.unmodifiableCollection(collection);
8331d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
8341d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
8351d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
8361d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns an unmodifiable view of the specified collection of entries. The
8371d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link Entry#setValue} operation throws an {@link
8381d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * UnsupportedOperationException}. If the specified collection is a {@code
8391d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Set}, the returned collection is also a {@code Set}.
8401d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
8411d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param entries the entries for which to return an unmodifiable view
8421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @return an unmodifiable view of the entries
8431d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
8440888a09821a98ac0680fad765217302858e70fa4Paul Duffin  private static <K, V> Collection<Entry<K, V>> unmodifiableEntries(
8450888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Collection<Entry<K, V>> entries) {
8461d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    if (entries instanceof Set) {
8471d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return Maps.unmodifiableEntrySet((Set<Entry<K, V>>) entries);
8481d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
8490888a09821a98ac0680fad765217302858e70fa4Paul Duffin    return new Maps.UnmodifiableEntries<K, V>(
8500888a09821a98ac0680fad765217302858e70fa4Paul Duffin        Collections.unmodifiableCollection(entries));
8511d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
8521d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
8531d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
8540888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * Returns {@link ListMultimap#asMap multimap.asMap()}, with its type
8550888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * corrected from {@code Map<K, Collection<V>>} to {@code Map<K, List<V>>}.
8560888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
8570888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * @since 15.0
8581d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
8590888a09821a98ac0680fad765217302858e70fa4Paul Duffin  @Beta
8600888a09821a98ac0680fad765217302858e70fa4Paul Duffin  @SuppressWarnings("unchecked")
8610888a09821a98ac0680fad765217302858e70fa4Paul Duffin  // safe by specification of ListMultimap.asMap()
8620888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> Map<K, List<V>> asMap(ListMultimap<K, V> multimap) {
8630888a09821a98ac0680fad765217302858e70fa4Paul Duffin    return (Map<K, List<V>>) (Map<K, ?>) multimap.asMap();
8641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
8651d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
8660888a09821a98ac0680fad765217302858e70fa4Paul Duffin  /**
8670888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * Returns {@link SetMultimap#asMap multimap.asMap()}, with its type corrected
8680888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * from {@code Map<K, Collection<V>>} to {@code Map<K, Set<V>>}.
8690888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
8700888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * @since 15.0
8710888a09821a98ac0680fad765217302858e70fa4Paul Duffin   */
8720888a09821a98ac0680fad765217302858e70fa4Paul Duffin  @Beta
8730888a09821a98ac0680fad765217302858e70fa4Paul Duffin  @SuppressWarnings("unchecked")
8740888a09821a98ac0680fad765217302858e70fa4Paul Duffin  // safe by specification of SetMultimap.asMap()
8750888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> Map<K, Set<V>> asMap(SetMultimap<K, V> multimap) {
8760888a09821a98ac0680fad765217302858e70fa4Paul Duffin    return (Map<K, Set<V>>) (Map<K, ?>) multimap.asMap();
8770888a09821a98ac0680fad765217302858e70fa4Paul Duffin  }
8781d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
8790888a09821a98ac0680fad765217302858e70fa4Paul Duffin  /**
8800888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * Returns {@link SortedSetMultimap#asMap multimap.asMap()}, with its type
8810888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * corrected from {@code Map<K, Collection<V>>} to
8820888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * {@code Map<K, SortedSet<V>>}.
8830888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
8840888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * @since 15.0
8850888a09821a98ac0680fad765217302858e70fa4Paul Duffin   */
8860888a09821a98ac0680fad765217302858e70fa4Paul Duffin  @Beta
8870888a09821a98ac0680fad765217302858e70fa4Paul Duffin  @SuppressWarnings("unchecked")
8880888a09821a98ac0680fad765217302858e70fa4Paul Duffin  // safe by specification of SortedSetMultimap.asMap()
8890888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> Map<K, SortedSet<V>> asMap(
8900888a09821a98ac0680fad765217302858e70fa4Paul Duffin      SortedSetMultimap<K, V> multimap) {
8910888a09821a98ac0680fad765217302858e70fa4Paul Duffin    return (Map<K, SortedSet<V>>) (Map<K, ?>) multimap.asMap();
8920888a09821a98ac0680fad765217302858e70fa4Paul Duffin  }
8931d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
8940888a09821a98ac0680fad765217302858e70fa4Paul Duffin  /**
8950888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * Returns {@link Multimap#asMap multimap.asMap()}. This is provided for
8960888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * parity with the other more strongly-typed {@code asMap()} implementations.
8970888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
8980888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * @since 15.0
8990888a09821a98ac0680fad765217302858e70fa4Paul Duffin   */
9000888a09821a98ac0680fad765217302858e70fa4Paul Duffin  @Beta
9010888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> Map<K, Collection<V>> asMap(Multimap<K, V> multimap) {
9020888a09821a98ac0680fad765217302858e70fa4Paul Duffin    return multimap.asMap();
9031d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
9041d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
9051d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
9061d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns a multimap view of the specified map. The multimap is backed by the
9071d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * map, so changes to the map are reflected in the multimap, and vice versa.
9081d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * If the map is modified while an iteration over one of the multimap's
9091d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * collection views is in progress (except through the iterator's own {@code
9101d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * remove} operation, or through the {@code setValue} operation on a map entry
9111d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * returned by the iterator), the results of the iteration are undefined.
9121d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
9131d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The multimap supports mapping removal, which removes the corresponding
9141d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * mapping from the map. It does not support any operations which might add
9151d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * mappings, such as {@code put}, {@code putAll} or {@code replaceValues}.
9161d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
9171d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The returned multimap will be serializable if the specified map is
9181d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * serializable.
9191d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
9201d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param map the backing map for the returned multimap view
9211d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
9221d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  public static <K, V> SetMultimap<K, V> forMap(Map<K, V> map) {
9231d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return new MapMultimap<K, V>(map);
9241d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
9251d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
9261d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /** @see Multimaps#forMap */
9270888a09821a98ac0680fad765217302858e70fa4Paul Duffin  private static class MapMultimap<K, V>
9280888a09821a98ac0680fad765217302858e70fa4Paul Duffin      extends AbstractMultimap<K, V> implements SetMultimap<K, V>, Serializable {
9291d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    final Map<K, V> map;
9301d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
9311d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    MapMultimap(Map<K, V> map) {
9321d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      this.map = checkNotNull(map);
9331d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
9341d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
9350888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
9361d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    public int size() {
9371d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return map.size();
9381d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
9391d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
9400888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
9411d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    public boolean containsKey(Object key) {
9421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return map.containsKey(key);
9431d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
9441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
9450888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
9461d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    public boolean containsValue(Object value) {
9471d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return map.containsValue(value);
9481d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
9491d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
9500888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
9511d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    public boolean containsEntry(Object key, Object value) {
9521d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return map.entrySet().contains(Maps.immutableEntry(key, value));
9531d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
9541d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
9550888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
9561d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    public Set<V> get(final K key) {
9577dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new Sets.ImprovedAbstractSet<V>() {
9580888a09821a98ac0680fad765217302858e70fa4Paul Duffin        @Override public Iterator<V> iterator() {
9591d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert          return new Iterator<V>() {
9601d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert            int i;
9611d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
9620888a09821a98ac0680fad765217302858e70fa4Paul Duffin            @Override
9631d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert            public boolean hasNext() {
9641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert              return (i == 0) && map.containsKey(key);
9651d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert            }
9661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
9670888a09821a98ac0680fad765217302858e70fa4Paul Duffin            @Override
9681d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert            public V next() {
9691d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert              if (!hasNext()) {
9701d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert                throw new NoSuchElementException();
9711d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert              }
9721d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert              i++;
9731d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert              return map.get(key);
9741d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert            }
9751d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
9760888a09821a98ac0680fad765217302858e70fa4Paul Duffin            @Override
9771d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert            public void remove() {
9780888a09821a98ac0680fad765217302858e70fa4Paul Duffin              checkRemove(i == 1);
9791d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert              i = -1;
9801d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert              map.remove(key);
9811d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert            }
9821d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert          };
9831d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        }
9841d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
9850888a09821a98ac0680fad765217302858e70fa4Paul Duffin        @Override public int size() {
9861d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert          return map.containsKey(key) ? 1 : 0;
9871d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        }
9881d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      };
9891d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
9901d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
9910888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
9921d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    public boolean put(K key, V value) {
9931d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
9941d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
9951d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
9960888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
9971d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    public boolean putAll(K key, Iterable<? extends V> values) {
9981d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
9991d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
10001d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
10010888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
10021d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    public boolean putAll(Multimap<? extends K, ? extends V> multimap) {
10031d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
10041d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
10051d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
10060888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
10071d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    public Set<V> replaceValues(K key, Iterable<? extends V> values) {
10081d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
10091d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
10101d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
10110888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
10121d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    public boolean remove(Object key, Object value) {
10131d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return map.entrySet().remove(Maps.immutableEntry(key, value));
10141d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
10151d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
10160888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
10171d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    public Set<V> removeAll(Object key) {
10181d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      Set<V> values = new HashSet<V>(2);
10191d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      if (!map.containsKey(key)) {
10201d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        return values;
10211d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
10221d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      values.add(map.remove(key));
10231d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return values;
10241d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
10251d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
10260888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
10271d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    public void clear() {
10281d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      map.clear();
10291d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
10301d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
10310888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
10321d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    public Set<K> keySet() {
10331d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return map.keySet();
10341d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
10351d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
10360888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
10371d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    public Collection<V> values() {
10381d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return map.values();
10391d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
10401d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
10410888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override
10421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    public Set<Entry<K, V>> entries() {
10431d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return map.entrySet();
10441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
10450888a09821a98ac0680fad765217302858e70fa4Paul Duffin
10467dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
10470888a09821a98ac0680fad765217302858e70fa4Paul Duffin    Iterator<Entry<K, V>> entryIterator() {
10480888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return map.entrySet().iterator();
10491d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
10501d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
10517dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
10520888a09821a98ac0680fad765217302858e70fa4Paul Duffin    Map<K, Collection<V>> createAsMap() {
10530888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return new AsMap<K, V>(this);
10541d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
10551d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
10560888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public int hashCode() {
10570888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return map.hashCode();
10581d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
10590888a09821a98ac0680fad765217302858e70fa4Paul Duffin
10601d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    private static final long serialVersionUID = 7845222491160860175L;
10611d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
10621d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
10631d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
10641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns a view of a multimap where each value is transformed by a function.
10651d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * All other properties of the multimap, such as iteration order, are left
10661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * intact. For example, the code: <pre>   {@code
10671d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
10681d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Multimap<String, Integer> multimap =
10691d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     ImmutableSetMultimap.of("a", 2, "b", -3, "b", -3, "a", 4, "c", 6);
10701d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Function<Integer, String> square = new Function<Integer, String>() {
10711d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     public String apply(Integer in) {
10721d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       return Integer.toString(in * in);
10731d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     }
10741d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * };
10751d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Multimap<String, String> transformed =
10761d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     Multimaps.transformValues(multimap, square);
10771d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   System.out.println(transformed);}</pre>
10781d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
10790888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * ... prints {@code {a=[4, 16], b=[9, 9], c=[36]}}.
10801d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
10811d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Changes in the underlying multimap are reflected in this view.
10821d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Conversely, this view supports removal operations, and these are reflected
10831d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * in the underlying multimap.
10841d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
10851d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>It's acceptable for the underlying multimap to contain null keys, and
10861d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * even null values provided that the function is capable of accepting null
10871d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * input.  The transformed multimap might contain null values, if the function
10881d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * sometimes gives a null result.
10891d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
10901d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The returned multimap is not thread-safe or serializable, even if the
10911d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * underlying multimap is.  The {@code equals} and {@code hashCode} methods
10921d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * of the returned multimap are meaningless, since there is not a definition
10931d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * of {@code equals} or {@code hashCode} for general collections, and
10941d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code get()} will return a general {@code Collection} as opposed to a
10951d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code List} or a {@code Set}.
10961d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
10971d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The function is applied lazily, invoked when needed. This is necessary
10981d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * for the returned multimap to be a view, but it means that the function will
10991d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * be applied many times for bulk operations like
11001d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link Multimap#containsValue} and {@code Multimap.toString()}. For this to
11011d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * perform well, {@code function} should be fast. To avoid lazy evaluation
11021d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * when the returned multimap doesn't need to be a view, copy the returned
11031d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap into a new multimap of your choosing.
11041d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
11051d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @since 7.0
11061d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
11070888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V1, V2> Multimap<K, V2> transformValues(
11080888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Multimap<K, V1> fromMultimap, final Function<? super V1, V2> function) {
11091d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    checkNotNull(function);
11100888a09821a98ac0680fad765217302858e70fa4Paul Duffin    EntryTransformer<K, V1, V2> transformer = Maps.asEntryTransformer(function);
11111d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return transformEntries(fromMultimap, transformer);
11121d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
11131d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
11141d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
11151d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns a view of a multimap whose values are derived from the original
11161d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap's entries. In contrast to {@link #transformValues}, this method's
11171d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * entry-transformation logic may depend on the key as well as the value.
11181d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
11191d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>All other properties of the transformed multimap, such as iteration
11201d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * order, are left intact. For example, the code: <pre>   {@code
11211d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
11221d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   SetMultimap<String, Integer> multimap =
11231d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       ImmutableSetMultimap.of("a", 1, "a", 4, "b", -6);
11241d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   EntryTransformer<String, Integer, String> transformer =
11251d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       new EntryTransformer<String, Integer, String>() {
11261d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *         public String transformEntry(String key, Integer value) {
11271d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *            return (value >= 0) ? key : "no" + key;
11281d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *         }
11291d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       };
11301d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   Multimap<String, String> transformed =
11311d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       Multimaps.transformEntries(multimap, transformer);
11321d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   System.out.println(transformed);}</pre>
11331d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
11341d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * ... prints {@code {a=[a, a], b=[nob]}}.
11351d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
11361d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Changes in the underlying multimap are reflected in this view.
11371d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Conversely, this view supports removal operations, and these are reflected
11381d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * in the underlying multimap.
11391d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
11401d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>It's acceptable for the underlying multimap to contain null keys and
11411d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * null values provided that the transformer is capable of accepting null
11421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * inputs. The transformed multimap might contain null values if the
11431d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * transformer sometimes gives a null result.
11441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
11451d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The returned multimap is not thread-safe or serializable, even if the
11461d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * underlying multimap is.  The {@code equals} and {@code hashCode} methods
11471d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * of the returned multimap are meaningless, since there is not a definition
11481d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * of {@code equals} or {@code hashCode} for general collections, and
11491d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code get()} will return a general {@code Collection} as opposed to a
11501d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code List} or a {@code Set}.
11511d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
11521d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The transformer is applied lazily, invoked when needed. This is
11531d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * necessary for the returned multimap to be a view, but it means that the
11541d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * transformer will be applied many times for bulk operations like {@link
11551d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Multimap#containsValue} and {@link Object#toString}. For this to perform
11561d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * well, {@code transformer} should be fast. To avoid lazy evaluation when the
11571d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * returned multimap doesn't need to be a view, copy the returned multimap
11581d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * into a new multimap of your choosing.
11591d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
11601d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p><b>Warning:</b> This method assumes that for any instance {@code k} of
11611d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code EntryTransformer} key type {@code K}, {@code k.equals(k2)} implies
11621d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * that {@code k2} is also of type {@code K}. Using an {@code
11631d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * EntryTransformer} key type for which this may not hold, such as {@code
11641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * ArrayList}, may risk a {@code ClassCastException} when calling methods on
11651d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * the transformed multimap.
11661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
11671d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @since 7.0
11681d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
11690888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V1, V2> Multimap<K, V2> transformEntries(
11700888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Multimap<K, V1> fromMap,
11711d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      EntryTransformer<? super K, ? super V1, V2> transformer) {
11721d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return new TransformedEntriesMultimap<K, V1, V2>(fromMap, transformer);
11731d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
11741d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
11750888a09821a98ac0680fad765217302858e70fa4Paul Duffin  private static class TransformedEntriesMultimap<K, V1, V2>
11760888a09821a98ac0680fad765217302858e70fa4Paul Duffin      extends AbstractMultimap<K, V2> {
11771d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    final Multimap<K, V1> fromMultimap;
11781d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    final EntryTransformer<? super K, ? super V1, V2> transformer;
11791d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
11801d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    TransformedEntriesMultimap(Multimap<K, V1> fromMultimap,
11811d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        final EntryTransformer<? super K, ? super V1, V2> transformer) {
11821d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      this.fromMultimap = checkNotNull(fromMultimap);
11831d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      this.transformer = checkNotNull(transformer);
11841d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
11851d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
11867dd252788645e940eada959bdde927426e2531c9Paul Duffin    Collection<V2> transform(K key, Collection<V1> values) {
11870888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Function<? super V1, V2> function =
11880888a09821a98ac0680fad765217302858e70fa4Paul Duffin          Maps.asValueToValueFunction(transformer, key);
11897dd252788645e940eada959bdde927426e2531c9Paul Duffin      if (values instanceof List) {
11907dd252788645e940eada959bdde927426e2531c9Paul Duffin        return Lists.transform((List<V1>) values, function);
11917dd252788645e940eada959bdde927426e2531c9Paul Duffin      } else {
11927dd252788645e940eada959bdde927426e2531c9Paul Duffin        return Collections2.transform(values, function);
11937dd252788645e940eada959bdde927426e2531c9Paul Duffin      }
11941d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
11951d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
11967dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
11977dd252788645e940eada959bdde927426e2531c9Paul Duffin    Map<K, Collection<V2>> createAsMap() {
11987dd252788645e940eada959bdde927426e2531c9Paul Duffin      return Maps.transformEntries(fromMultimap.asMap(),
11997dd252788645e940eada959bdde927426e2531c9Paul Duffin          new EntryTransformer<K, Collection<V1>, Collection<V2>>() {
12000888a09821a98ac0680fad765217302858e70fa4Paul Duffin        @Override public Collection<V2> transformEntry(
12010888a09821a98ac0680fad765217302858e70fa4Paul Duffin            K key, Collection<V1> value) {
12020888a09821a98ac0680fad765217302858e70fa4Paul Duffin          return transform(key, value);
12030888a09821a98ac0680fad765217302858e70fa4Paul Duffin        }
12040888a09821a98ac0680fad765217302858e70fa4Paul Duffin      });
12051d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
12061d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
12070888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public void clear() {
12081d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      fromMultimap.clear();
12091d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
12101d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
12110888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public boolean containsKey(Object key) {
12121d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return fromMultimap.containsKey(key);
12131d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
12141d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
12157dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
12167dd252788645e940eada959bdde927426e2531c9Paul Duffin    Iterator<Entry<K, V2>> entryIterator() {
12170888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return Iterators.transform(fromMultimap.entries().iterator(),
12180888a09821a98ac0680fad765217302858e70fa4Paul Duffin          Maps.<K, V1, V2>asEntryToEntryFunction(transformer));
12191d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
12201d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
12210888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Collection<V2> get(final K key) {
12221d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return transform(key, fromMultimap.get(key));
12231d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
12241d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
12250888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public boolean isEmpty() {
12261d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return fromMultimap.isEmpty();
12271d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
12281d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
12290888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Set<K> keySet() {
12301d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return fromMultimap.keySet();
12311d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
12321d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
12330888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Multiset<K> keys() {
12341d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return fromMultimap.keys();
12351d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
12361d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
12370888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public boolean put(K key, V2 value) {
12381d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
12391d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
12401d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
12410888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public boolean putAll(K key, Iterable<? extends V2> values) {
12421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
12431d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
12441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
12450888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public boolean putAll(
12460888a09821a98ac0680fad765217302858e70fa4Paul Duffin        Multimap<? extends K, ? extends V2> multimap) {
12471d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
12481d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
12491d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
12501d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @SuppressWarnings("unchecked")
12510888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public boolean remove(Object key, Object value) {
12521d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return get((K) key).remove(value);
12531d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
12541d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
12551d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @SuppressWarnings("unchecked")
12560888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Collection<V2> removeAll(Object key) {
12571d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return transform((K) key, fromMultimap.removeAll(key));
12581d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
12591d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
12600888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Collection<V2> replaceValues(
12610888a09821a98ac0680fad765217302858e70fa4Paul Duffin        K key, Iterable<? extends V2> values) {
12621d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
12631d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
12641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
12650888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public int size() {
12661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return fromMultimap.size();
12671d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
12680888a09821a98ac0680fad765217302858e70fa4Paul Duffin
12697dd252788645e940eada959bdde927426e2531c9Paul Duffin    @Override
12707dd252788645e940eada959bdde927426e2531c9Paul Duffin    Collection<V2> createValues() {
12710888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return Collections2.transform(
12720888a09821a98ac0680fad765217302858e70fa4Paul Duffin          fromMultimap.entries(), Maps.<K, V1, V2>asEntryToValueFunction(transformer));
12731d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
12741d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
12751d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
12761d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
12771d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns a view of a {@code ListMultimap} where each value is transformed by
12781d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * a function. All other properties of the multimap, such as iteration order,
12791d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * are left intact. For example, the code: <pre>   {@code
12801d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
12811d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   ListMultimap<String, Integer> multimap
12821d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *        = ImmutableListMultimap.of("a", 4, "a", 16, "b", 9);
12831d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   Function<Integer, Double> sqrt =
12841d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       new Function<Integer, Double>() {
12851d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *         public Double apply(Integer in) {
12861d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *           return Math.sqrt((int) in);
12871d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *         }
12881d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       };
12891d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   ListMultimap<String, Double> transformed = Multimaps.transformValues(map,
12901d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       sqrt);
12911d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   System.out.println(transformed);}</pre>
12921d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
12931d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * ... prints {@code {a=[2.0, 4.0], b=[3.0]}}.
12941d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
12951d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Changes in the underlying multimap are reflected in this view.
12961d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Conversely, this view supports removal operations, and these are reflected
12971d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * in the underlying multimap.
12981d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
12991d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>It's acceptable for the underlying multimap to contain null keys, and
13001d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * even null values provided that the function is capable of accepting null
13011d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * input.  The transformed multimap might contain null values, if the function
13021d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * sometimes gives a null result.
13031d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
13041d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The returned multimap is not thread-safe or serializable, even if the
13051d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * underlying multimap is.
13061d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
13071d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The function is applied lazily, invoked when needed. This is necessary
13081d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * for the returned multimap to be a view, but it means that the function will
13091d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * be applied many times for bulk operations like
13101d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link Multimap#containsValue} and {@code Multimap.toString()}. For this to
13111d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * perform well, {@code function} should be fast. To avoid lazy evaluation
13121d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * when the returned multimap doesn't need to be a view, copy the returned
13131d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * multimap into a new multimap of your choosing.
13141d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
13151d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @since 7.0
13161d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
13170888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V1, V2> ListMultimap<K, V2> transformValues(
13180888a09821a98ac0680fad765217302858e70fa4Paul Duffin      ListMultimap<K, V1> fromMultimap,
13191d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      final Function<? super V1, V2> function) {
13201d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    checkNotNull(function);
13210888a09821a98ac0680fad765217302858e70fa4Paul Duffin    EntryTransformer<K, V1, V2> transformer = Maps.asEntryTransformer(function);
13221d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return transformEntries(fromMultimap, transformer);
13231d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
13241d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
13251d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
13261d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns a view of a {@code ListMultimap} whose values are derived from the
13271d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * original multimap's entries. In contrast to
13281d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@link #transformValues(ListMultimap, Function)}, this method's
13291d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * entry-transformation logic may depend on the key as well as the value.
13301d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
13311d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>All other properties of the transformed multimap, such as iteration
13321d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * order, are left intact. For example, the code: <pre>   {@code
13331d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
13341d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   Multimap<String, Integer> multimap =
13351d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       ImmutableMultimap.of("a", 1, "a", 4, "b", 6);
13361d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   EntryTransformer<String, Integer, String> transformer =
13371d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       new EntryTransformer<String, Integer, String>() {
13381d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *         public String transformEntry(String key, Integer value) {
13391d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *           return key + value;
13401d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *         }
13411d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       };
13421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   Multimap<String, String> transformed =
13431d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       Multimaps.transformEntries(multimap, transformer);
13441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   System.out.println(transformed);}</pre>
13451d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
13461d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * ... prints {@code {"a"=["a1", "a4"], "b"=["b6"]}}.
13471d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
13481d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Changes in the underlying multimap are reflected in this view.
13491d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Conversely, this view supports removal operations, and these are reflected
13501d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * in the underlying multimap.
13511d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
13521d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>It's acceptable for the underlying multimap to contain null keys and
13531d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * null values provided that the transformer is capable of accepting null
13541d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * inputs. The transformed multimap might contain null values if the
13551d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * transformer sometimes gives a null result.
13561d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
13571d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The returned multimap is not thread-safe or serializable, even if the
13581d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * underlying multimap is.
13591d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
13601d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The transformer is applied lazily, invoked when needed. This is
13611d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * necessary for the returned multimap to be a view, but it means that the
13621d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * transformer will be applied many times for bulk operations like {@link
13631d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Multimap#containsValue} and {@link Object#toString}. For this to perform
13641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * well, {@code transformer} should be fast. To avoid lazy evaluation when the
13651d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * returned multimap doesn't need to be a view, copy the returned multimap
13661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * into a new multimap of your choosing.
13671d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
13681d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p><b>Warning:</b> This method assumes that for any instance {@code k} of
13691d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code EntryTransformer} key type {@code K}, {@code k.equals(k2)} implies
13701d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * that {@code k2} is also of type {@code K}. Using an {@code
13711d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * EntryTransformer} key type for which this may not hold, such as {@code
13721d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * ArrayList}, may risk a {@code ClassCastException} when calling methods on
13731d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * the transformed multimap.
13741d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
13751d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @since 7.0
13761d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
13770888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V1, V2> ListMultimap<K, V2> transformEntries(
13780888a09821a98ac0680fad765217302858e70fa4Paul Duffin      ListMultimap<K, V1> fromMap,
13791d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      EntryTransformer<? super K, ? super V1, V2> transformer) {
13801d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return new TransformedEntriesListMultimap<K, V1, V2>(fromMap, transformer);
13811d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
13821d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
13830888a09821a98ac0680fad765217302858e70fa4Paul Duffin  private static final class TransformedEntriesListMultimap<K, V1, V2>
13840888a09821a98ac0680fad765217302858e70fa4Paul Duffin      extends TransformedEntriesMultimap<K, V1, V2>
13850888a09821a98ac0680fad765217302858e70fa4Paul Duffin      implements ListMultimap<K, V2> {
13861d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
13871d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    TransformedEntriesListMultimap(ListMultimap<K, V1> fromMultimap,
13881d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        EntryTransformer<? super K, ? super V1, V2> transformer) {
13891d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      super(fromMultimap, transformer);
13901d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
13911d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
13920888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override List<V2> transform(K key, Collection<V1> values) {
13930888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return Lists.transform((List<V1>) values, Maps.asValueToValueFunction(transformer, key));
13941d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
13951d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
13960888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public List<V2> get(K key) {
13971d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return transform(key, fromMultimap.get(key));
13981d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
13991d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
14001d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @SuppressWarnings("unchecked")
14010888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public List<V2> removeAll(Object key) {
14021d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return transform((K) key, fromMultimap.removeAll(key));
14031d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
14041d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
14050888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public List<V2> replaceValues(
14060888a09821a98ac0680fad765217302858e70fa4Paul Duffin        K key, Iterable<? extends V2> values) {
14071d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      throw new UnsupportedOperationException();
14081d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
14091d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
14101d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
14111d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
14121d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Creates an index {@code ImmutableListMultimap} that contains the results of
14131d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * applying a specified function to each item in an {@code Iterable} of
14141d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * values. Each value will be stored as a value in the resulting multimap,
14151d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * yielding a multimap with the same size as the input iterable. The key used
14161d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * to store that value in the multimap will be the result of calling the
14171d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * function on that value. The resulting multimap is created as an immutable
14181d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * snapshot. In the returned multimap, keys appear in the order they are first
14191d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * encountered, and the values corresponding to each key appear in the same
14201d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * order as they are encountered.
14211d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
14221d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>For example, <pre>   {@code
14231d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
14241d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   List<String> badGuys =
14251d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       Arrays.asList("Inky", "Blinky", "Pinky", "Pinky", "Clyde");
14261d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   Function<String, Integer> stringLengthFunction = ...;
14271d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   Multimap<Integer, String> index =
14281d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       Multimaps.index(badGuys, stringLengthFunction);
14291d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   System.out.println(index);}</pre>
14301d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
14310888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>prints <pre>   {@code
14321d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
14331d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   {4=[Inky], 6=[Blinky], 5=[Pinky, Pinky, Clyde]}}</pre>
14341d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
14350888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>The returned multimap is serializable if its keys and values are all
14361d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * serializable.
14371d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
14381d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param values the values to use when constructing the {@code
14391d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     ImmutableListMultimap}
14401d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param keyFunction the function used to produce the key for each value
14411d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @return {@code ImmutableListMultimap} mapping the result of evaluating the
14421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     function {@code keyFunction} on each value in the input collection to
14431d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     that value
14441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @throws NullPointerException if any of the following cases is true:
14451d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     <ul>
14461d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     <li>{@code values} is null
14471d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     <li>{@code keyFunction} is null
14481d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     <li>An element in {@code values} is null
14491d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     <li>{@code keyFunction} returns {@code null} for any element of {@code
14501d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *         values}
14511d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     </ul>
14521d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
14530888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> ImmutableListMultimap<K, V> index(
14540888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Iterable<V> values, Function<? super V, K> keyFunction) {
14551d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return index(values.iterator(), keyFunction);
14561d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
14571d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
14581d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
14591d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Creates an index {@code ImmutableListMultimap} that contains the results of
14601d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * applying a specified function to each item in an {@code Iterator} of
14611d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * values. Each value will be stored as a value in the resulting multimap,
14621d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * yielding a multimap with the same size as the input iterator. The key used
14631d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * to store that value in the multimap will be the result of calling the
14641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * function on that value. The resulting multimap is created as an immutable
14651d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * snapshot. In the returned multimap, keys appear in the order they are first
14661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * encountered, and the values corresponding to each key appear in the same
14671d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * order as they are encountered.
14681d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
14691d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>For example, <pre>   {@code
14701d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
14711d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   List<String> badGuys =
14721d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       Arrays.asList("Inky", "Blinky", "Pinky", "Pinky", "Clyde");
14731d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   Function<String, Integer> stringLengthFunction = ...;
14741d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   Multimap<Integer, String> index =
14751d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *       Multimaps.index(badGuys.iterator(), stringLengthFunction);
14761d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   System.out.println(index);}</pre>
14771d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
14780888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>prints <pre>   {@code
14791d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
14801d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *   {4=[Inky], 6=[Blinky], 5=[Pinky, Pinky, Clyde]}}</pre>
14811d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
14820888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>The returned multimap is serializable if its keys and values are all
14831d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * serializable.
14841d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
14851d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param values the values to use when constructing the {@code
14861d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     ImmutableListMultimap}
14871d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @param keyFunction the function used to produce the key for each value
14881d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @return {@code ImmutableListMultimap} mapping the result of evaluating the
14891d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     function {@code keyFunction} on each value in the input collection to
14901d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     that value
14911d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @throws NullPointerException if any of the following cases is true:
14921d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     <ul>
14931d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     <li>{@code values} is null
14941d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     <li>{@code keyFunction} is null
14951d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     <li>An element in {@code values} is null
14961d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     <li>{@code keyFunction} returns {@code null} for any element of {@code
14971d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *         values}
14981d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *     </ul>
14991d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @since 10.0
15001d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
15010888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> ImmutableListMultimap<K, V> index(
15020888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Iterator<V> values, Function<? super V, K> keyFunction) {
15031d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    checkNotNull(keyFunction);
15040888a09821a98ac0680fad765217302858e70fa4Paul Duffin    ImmutableListMultimap.Builder<K, V> builder
15050888a09821a98ac0680fad765217302858e70fa4Paul Duffin        = ImmutableListMultimap.builder();
15061d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    while (values.hasNext()) {
15071d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      V value = values.next();
15081d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      checkNotNull(value, values);
15091d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      builder.put(keyFunction.apply(value), value);
15101d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
15111d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    return builder.build();
15121d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
15131d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
15147dd252788645e940eada959bdde927426e2531c9Paul Duffin  static class Keys<K, V> extends AbstractMultiset<K> {
15157dd252788645e940eada959bdde927426e2531c9Paul Duffin    final Multimap<K, V> multimap;
15167dd252788645e940eada959bdde927426e2531c9Paul Duffin
15177dd252788645e940eada959bdde927426e2531c9Paul Duffin    Keys(Multimap<K, V> multimap) {
15187dd252788645e940eada959bdde927426e2531c9Paul Duffin      this.multimap = multimap;
15197dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
15201d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
15211d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @Override Iterator<Multiset.Entry<K>> entryIterator() {
15227dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new TransformedIterator<Map.Entry<K, Collection<V>>, Multiset.Entry<K>>(
15237dd252788645e940eada959bdde927426e2531c9Paul Duffin          multimap.asMap().entrySet().iterator()) {
15247dd252788645e940eada959bdde927426e2531c9Paul Duffin        @Override
15250888a09821a98ac0680fad765217302858e70fa4Paul Duffin        Multiset.Entry<K> transform(
15260888a09821a98ac0680fad765217302858e70fa4Paul Duffin            final Map.Entry<K, Collection<V>> backingEntry) {
15271d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert          return new Multisets.AbstractEntry<K>() {
15280888a09821a98ac0680fad765217302858e70fa4Paul Duffin            @Override
15297dd252788645e940eada959bdde927426e2531c9Paul Duffin            public K getElement() {
15301d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert              return backingEntry.getKey();
15311d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert            }
15321d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
15330888a09821a98ac0680fad765217302858e70fa4Paul Duffin            @Override
15347dd252788645e940eada959bdde927426e2531c9Paul Duffin            public int getCount() {
15351d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert              return backingEntry.getValue().size();
15361d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert            }
15371d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert          };
15381d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        }
15391d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      };
15401d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
15411d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
15421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @Override int distinctElements() {
15437dd252788645e940eada959bdde927426e2531c9Paul Duffin      return multimap.asMap().size();
15441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
15451d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
15460888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override Set<Multiset.Entry<K>> createEntrySet() {
15471d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return new KeysEntrySet();
15481d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
15491d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
15501d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    class KeysEntrySet extends Multisets.EntrySet<K> {
15510888a09821a98ac0680fad765217302858e70fa4Paul Duffin      @Override Multiset<K> multiset() {
15521d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        return Keys.this;
15531d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
15541d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
15550888a09821a98ac0680fad765217302858e70fa4Paul Duffin      @Override public Iterator<Multiset.Entry<K>> iterator() {
15561d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        return entryIterator();
15571d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
15581d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
15590888a09821a98ac0680fad765217302858e70fa4Paul Duffin      @Override public int size() {
15601d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        return distinctElements();
15611d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
15621d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
15631d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      @Override public boolean isEmpty() {
15647dd252788645e940eada959bdde927426e2531c9Paul Duffin        return multimap.isEmpty();
15651d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
15661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
15670888a09821a98ac0680fad765217302858e70fa4Paul Duffin      @Override public boolean contains(@Nullable Object o) {
15687dd252788645e940eada959bdde927426e2531c9Paul Duffin        if (o instanceof Multiset.Entry) {
15691d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert          Multiset.Entry<?> entry = (Multiset.Entry<?>) o;
15707dd252788645e940eada959bdde927426e2531c9Paul Duffin          Collection<V> collection = multimap.asMap().get(entry.getElement());
15711d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert          return collection != null && collection.size() == entry.getCount();
15721d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        }
15731d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        return false;
15741d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
15751d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
15760888a09821a98ac0680fad765217302858e70fa4Paul Duffin      @Override public boolean remove(@Nullable Object o) {
15777dd252788645e940eada959bdde927426e2531c9Paul Duffin        if (o instanceof Multiset.Entry) {
15781d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert          Multiset.Entry<?> entry = (Multiset.Entry<?>) o;
15797dd252788645e940eada959bdde927426e2531c9Paul Duffin          Collection<V> collection = multimap.asMap().get(entry.getElement());
15801d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert          if (collection != null && collection.size() == entry.getCount()) {
15811d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert            collection.clear();
15821d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert            return true;
15831d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert          }
15841d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        }
15851d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        return false;
15861d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
15871d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
15881d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
15891d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @Override public boolean contains(@Nullable Object element) {
15907dd252788645e940eada959bdde927426e2531c9Paul Duffin      return multimap.containsKey(element);
15911d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
15921d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
15931d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @Override public Iterator<K> iterator() {
15947dd252788645e940eada959bdde927426e2531c9Paul Duffin      return Maps.keyIterator(multimap.entries().iterator());
15951d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
15961d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
15971d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @Override public int count(@Nullable Object element) {
15987dd252788645e940eada959bdde927426e2531c9Paul Duffin      Collection<V> values = Maps.safeGet(multimap.asMap(), element);
15997dd252788645e940eada959bdde927426e2531c9Paul Duffin      return (values == null) ? 0 : values.size();
16001d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
16011d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
16020888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public int remove(@Nullable Object element, int occurrences) {
16030888a09821a98ac0680fad765217302858e70fa4Paul Duffin      checkNonnegative(occurrences, "occurrences");
16041d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      if (occurrences == 0) {
16051d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        return count(element);
16061d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
16071d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
16087dd252788645e940eada959bdde927426e2531c9Paul Duffin      Collection<V> values = Maps.safeGet(multimap.asMap(), element);
16091d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
16101d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      if (values == null) {
16111d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        return 0;
16121d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
16131d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
16141d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      int oldCount = values.size();
16151d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      if (occurrences >= oldCount) {
16161d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        values.clear();
16171d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      } else {
16181d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        Iterator<V> iterator = values.iterator();
16191d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        for (int i = 0; i < occurrences; i++) {
16201d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert          iterator.next();
16211d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert          iterator.remove();
16221d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        }
16231d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
16241d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return oldCount;
16251d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
16261d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
16271d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @Override public void clear() {
16287dd252788645e940eada959bdde927426e2531c9Paul Duffin      multimap.clear();
16291d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
16301d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
16311d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @Override public Set<K> elementSet() {
16327dd252788645e940eada959bdde927426e2531c9Paul Duffin      return multimap.keySet();
16331d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
16341d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
16351d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
16361d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
16371d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * A skeleton implementation of {@link Multimap#entries()}.
16381d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
16390888a09821a98ac0680fad765217302858e70fa4Paul Duffin  abstract static class Entries<K, V> extends
16400888a09821a98ac0680fad765217302858e70fa4Paul Duffin      AbstractCollection<Map.Entry<K, V>> {
16411d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    abstract Multimap<K, V> multimap();
16421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
16430888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public int size() {
16441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return multimap().size();
16451d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
16461d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
16470888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public boolean contains(@Nullable Object o) {
16487dd252788645e940eada959bdde927426e2531c9Paul Duffin      if (o instanceof Map.Entry) {
16491d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        Map.Entry<?, ?> entry = (Map.Entry<?, ?>) o;
16501d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        return multimap().containsEntry(entry.getKey(), entry.getValue());
16511d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
16521d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return false;
16531d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
16541d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
16550888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public boolean remove(@Nullable Object o) {
16567dd252788645e940eada959bdde927426e2531c9Paul Duffin      if (o instanceof Map.Entry) {
16571d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        Map.Entry<?, ?> entry = (Map.Entry<?, ?>) o;
16581d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        return multimap().remove(entry.getKey(), entry.getValue());
16591d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
16601d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return false;
16611d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
16621d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
16630888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public void clear() {
16641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      multimap().clear();
16651d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
16661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
16671d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
16681d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
16690888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * A skeleton implementation of {@link Multimap#asMap()}.
16701d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
16710888a09821a98ac0680fad765217302858e70fa4Paul Duffin  static final class AsMap<K, V> extends
16720888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Maps.ImprovedAbstractMap<K, Collection<V>> {
16730888a09821a98ac0680fad765217302858e70fa4Paul Duffin    private final Multimap<K, V> multimap;
16740888a09821a98ac0680fad765217302858e70fa4Paul Duffin
16750888a09821a98ac0680fad765217302858e70fa4Paul Duffin    AsMap(Multimap<K, V> multimap) {
16760888a09821a98ac0680fad765217302858e70fa4Paul Duffin      this.multimap = checkNotNull(multimap);
16771d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
16781d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
16790888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public int size() {
16800888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return multimap.keySet().size();
16811d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
16821d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
16830888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override protected Set<Entry<K, Collection<V>>> createEntrySet() {
16841d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      return new EntrySet();
16851d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
16861d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
16877dd252788645e940eada959bdde927426e2531c9Paul Duffin    void removeValuesForKey(Object key) {
16880888a09821a98ac0680fad765217302858e70fa4Paul Duffin      multimap.keySet().remove(key);
16891d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
16901d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
16911d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    class EntrySet extends Maps.EntrySet<K, Collection<V>> {
16920888a09821a98ac0680fad765217302858e70fa4Paul Duffin      @Override Map<K, Collection<V>> map() {
16931d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        return AsMap.this;
16941d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
16951d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
16960888a09821a98ac0680fad765217302858e70fa4Paul Duffin      @Override public Iterator<Entry<K, Collection<V>>> iterator() {
16970888a09821a98ac0680fad765217302858e70fa4Paul Duffin        return Maps.asMapEntryIterator(multimap.keySet(), new Function<K, Collection<V>>() {
16980888a09821a98ac0680fad765217302858e70fa4Paul Duffin          @Override
16990888a09821a98ac0680fad765217302858e70fa4Paul Duffin          public Collection<V> apply(K key) {
17000888a09821a98ac0680fad765217302858e70fa4Paul Duffin            return multimap.get(key);
17010888a09821a98ac0680fad765217302858e70fa4Paul Duffin          }
17020888a09821a98ac0680fad765217302858e70fa4Paul Duffin        });
17031d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
17041d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
17050888a09821a98ac0680fad765217302858e70fa4Paul Duffin      @Override public boolean remove(Object o) {
17061d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        if (!contains(o)) {
17071d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert          return false;
17081d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        }
17091d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        Map.Entry<?, ?> entry = (Map.Entry<?, ?>) o;
17101d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        removeValuesForKey(entry.getKey());
17111d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert        return true;
17121d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      }
17131d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
17141d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
17151d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    @SuppressWarnings("unchecked")
17160888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Collection<V> get(Object key) {
17170888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return containsKey(key) ? multimap.get((K) key) : null;
17181d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
17191d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
17200888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Collection<V> remove(Object key) {
17210888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return containsKey(key) ? multimap.removeAll(key) : null;
17221d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
17231d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
17240888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public Set<K> keySet() {
17250888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return multimap.keySet();
17261d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
17271d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
17280888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public boolean isEmpty() {
17290888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return multimap.isEmpty();
17301d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
17311d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
17320888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public boolean containsKey(Object key) {
17330888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return multimap.containsKey(key);
17341d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
17351d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
17360888a09821a98ac0680fad765217302858e70fa4Paul Duffin    @Override public void clear() {
17370888a09821a98ac0680fad765217302858e70fa4Paul Duffin      multimap.clear();
17381d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    }
17391d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
17401d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
17411d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
17421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns a multimap containing the mappings in {@code unfiltered} whose keys
17431d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * satisfy a predicate. The returned multimap is a live view of
17441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code unfiltered}; changes to one affect the other.
17451d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
17461d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The resulting multimap's views have iterators that don't support
17471d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code remove()}, but all other methods are supported by the multimap and
17481d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * its views. When adding a key that doesn't satisfy the predicate, the
17497dd252788645e940eada959bdde927426e2531c9Paul Duffin   * multimap's {@code put()}, {@code putAll()}, and {@code replaceValues()}
17507dd252788645e940eada959bdde927426e2531c9Paul Duffin   * methods throw an {@link IllegalArgumentException}.
17511d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
17521d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>When methods such as {@code removeAll()} and {@code clear()} are called on
17531d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * the filtered multimap or its views, only mappings whose keys satisfy the
17541d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * filter will be removed from the underlying multimap.
17551d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
17561d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The returned multimap isn't threadsafe or serializable, even if
17571d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code unfiltered} is.
17581d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
17591d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Many of the filtered multimap's methods, such as {@code size()}, iterate
17601d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * across every key/value mapping in the underlying multimap and determine
17611d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * which satisfy the filter. When a live view is <i>not</i> needed, it may be
17621d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * faster to copy the filtered multimap and use the copy.
17631d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
17641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p><b>Warning:</b> {@code keyPredicate} must be <i>consistent with equals</i>,
17651d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * as documented at {@link Predicate#apply}. Do not provide a predicate such
17661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * as {@code Predicates.instanceOf(ArrayList.class)}, which is inconsistent
17671d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * with equals.
17681d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
17691d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @since 11.0
17701d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
17710888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> Multimap<K, V> filterKeys(
17720888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Multimap<K, V> unfiltered, final Predicate<? super K> keyPredicate) {
17730888a09821a98ac0680fad765217302858e70fa4Paul Duffin    if (unfiltered instanceof SetMultimap) {
17740888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return filterKeys((SetMultimap<K, V>) unfiltered, keyPredicate);
17750888a09821a98ac0680fad765217302858e70fa4Paul Duffin    } else if (unfiltered instanceof ListMultimap) {
17760888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return filterKeys((ListMultimap<K, V>) unfiltered, keyPredicate);
17770888a09821a98ac0680fad765217302858e70fa4Paul Duffin    } else if (unfiltered instanceof FilteredKeyMultimap) {
17787dd252788645e940eada959bdde927426e2531c9Paul Duffin      FilteredKeyMultimap<K, V> prev = (FilteredKeyMultimap<K, V>) unfiltered;
17790888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return new FilteredKeyMultimap<K, V>(prev.unfiltered,
17800888a09821a98ac0680fad765217302858e70fa4Paul Duffin          Predicates.and(prev.keyPredicate, keyPredicate));
17817dd252788645e940eada959bdde927426e2531c9Paul Duffin    } else if (unfiltered instanceof FilteredMultimap) {
17827dd252788645e940eada959bdde927426e2531c9Paul Duffin      FilteredMultimap<K, V> prev = (FilteredMultimap<K, V>) unfiltered;
17830888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return filterFiltered(prev, Maps.<K>keyPredicateOnEntries(keyPredicate));
17847dd252788645e940eada959bdde927426e2531c9Paul Duffin    } else {
17857dd252788645e940eada959bdde927426e2531c9Paul Duffin      return new FilteredKeyMultimap<K, V>(unfiltered, keyPredicate);
17867dd252788645e940eada959bdde927426e2531c9Paul Duffin    }
17871d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
17880888a09821a98ac0680fad765217302858e70fa4Paul Duffin
17890888a09821a98ac0680fad765217302858e70fa4Paul Duffin  /**
17900888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * Returns a multimap containing the mappings in {@code unfiltered} whose keys
17910888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * satisfy a predicate. The returned multimap is a live view of
17920888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * {@code unfiltered}; changes to one affect the other.
17930888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
17940888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>The resulting multimap's views have iterators that don't support
17950888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * {@code remove()}, but all other methods are supported by the multimap and
17960888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * its views. When adding a key that doesn't satisfy the predicate, the
17970888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * multimap's {@code put()}, {@code putAll()}, and {@code replaceValues()}
17980888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * methods throw an {@link IllegalArgumentException}.
17990888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
18000888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>When methods such as {@code removeAll()} and {@code clear()} are called on
18010888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * the filtered multimap or its views, only mappings whose keys satisfy the
18020888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * filter will be removed from the underlying multimap.
18030888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
18040888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>The returned multimap isn't threadsafe or serializable, even if
18050888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * {@code unfiltered} is.
18060888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
18070888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>Many of the filtered multimap's methods, such as {@code size()}, iterate
18080888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * across every key/value mapping in the underlying multimap and determine
18090888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * which satisfy the filter. When a live view is <i>not</i> needed, it may be
18100888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * faster to copy the filtered multimap and use the copy.
18110888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
18120888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p><b>Warning:</b> {@code keyPredicate} must be <i>consistent with equals</i>,
18130888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * as documented at {@link Predicate#apply}. Do not provide a predicate such
18140888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * as {@code Predicates.instanceOf(ArrayList.class)}, which is inconsistent
18150888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * with equals.
18160888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
18170888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * @since 14.0
18180888a09821a98ac0680fad765217302858e70fa4Paul Duffin   */
18190888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> SetMultimap<K, V> filterKeys(
18200888a09821a98ac0680fad765217302858e70fa4Paul Duffin      SetMultimap<K, V> unfiltered, final Predicate<? super K> keyPredicate) {
18210888a09821a98ac0680fad765217302858e70fa4Paul Duffin    if (unfiltered instanceof FilteredKeySetMultimap) {
18220888a09821a98ac0680fad765217302858e70fa4Paul Duffin      FilteredKeySetMultimap<K, V> prev = (FilteredKeySetMultimap<K, V>) unfiltered;
18230888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return new FilteredKeySetMultimap<K, V>(prev.unfiltered(),
18240888a09821a98ac0680fad765217302858e70fa4Paul Duffin          Predicates.and(prev.keyPredicate, keyPredicate));
18250888a09821a98ac0680fad765217302858e70fa4Paul Duffin    } else if (unfiltered instanceof FilteredSetMultimap) {
18260888a09821a98ac0680fad765217302858e70fa4Paul Duffin      FilteredSetMultimap<K, V> prev = (FilteredSetMultimap<K, V>) unfiltered;
18270888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return filterFiltered(prev, Maps.<K>keyPredicateOnEntries(keyPredicate));
18280888a09821a98ac0680fad765217302858e70fa4Paul Duffin    } else {
18290888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return new FilteredKeySetMultimap<K, V>(unfiltered, keyPredicate);
18300888a09821a98ac0680fad765217302858e70fa4Paul Duffin    }
18310888a09821a98ac0680fad765217302858e70fa4Paul Duffin  }
18320888a09821a98ac0680fad765217302858e70fa4Paul Duffin
18330888a09821a98ac0680fad765217302858e70fa4Paul Duffin  /**
18340888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * Returns a multimap containing the mappings in {@code unfiltered} whose keys
18350888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * satisfy a predicate. The returned multimap is a live view of
18360888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * {@code unfiltered}; changes to one affect the other.
18370888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
18380888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>The resulting multimap's views have iterators that don't support
18390888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * {@code remove()}, but all other methods are supported by the multimap and
18400888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * its views. When adding a key that doesn't satisfy the predicate, the
18410888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * multimap's {@code put()}, {@code putAll()}, and {@code replaceValues()}
18420888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * methods throw an {@link IllegalArgumentException}.
18430888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
18440888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>When methods such as {@code removeAll()} and {@code clear()} are called on
18450888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * the filtered multimap or its views, only mappings whose keys satisfy the
18460888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * filter will be removed from the underlying multimap.
18470888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
18480888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>The returned multimap isn't threadsafe or serializable, even if
18490888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * {@code unfiltered} is.
18500888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
18510888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>Many of the filtered multimap's methods, such as {@code size()}, iterate
18520888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * across every key/value mapping in the underlying multimap and determine
18530888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * which satisfy the filter. When a live view is <i>not</i> needed, it may be
18540888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * faster to copy the filtered multimap and use the copy.
18550888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
18560888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p><b>Warning:</b> {@code keyPredicate} must be <i>consistent with equals</i>,
18570888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * as documented at {@link Predicate#apply}. Do not provide a predicate such
18580888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * as {@code Predicates.instanceOf(ArrayList.class)}, which is inconsistent
18590888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * with equals.
18600888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
18610888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * @since 14.0
18620888a09821a98ac0680fad765217302858e70fa4Paul Duffin   */
18630888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> ListMultimap<K, V> filterKeys(
18640888a09821a98ac0680fad765217302858e70fa4Paul Duffin      ListMultimap<K, V> unfiltered, final Predicate<? super K> keyPredicate) {
18650888a09821a98ac0680fad765217302858e70fa4Paul Duffin    if (unfiltered instanceof FilteredKeyListMultimap) {
18660888a09821a98ac0680fad765217302858e70fa4Paul Duffin      FilteredKeyListMultimap<K, V> prev = (FilteredKeyListMultimap<K, V>) unfiltered;
18670888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return new FilteredKeyListMultimap<K, V>(prev.unfiltered(),
18680888a09821a98ac0680fad765217302858e70fa4Paul Duffin          Predicates.and(prev.keyPredicate, keyPredicate));
18690888a09821a98ac0680fad765217302858e70fa4Paul Duffin    } else {
18700888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return new FilteredKeyListMultimap<K, V>(unfiltered, keyPredicate);
18710888a09821a98ac0680fad765217302858e70fa4Paul Duffin    }
18720888a09821a98ac0680fad765217302858e70fa4Paul Duffin  }
18731d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
18741d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
18751d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns a multimap containing the mappings in {@code unfiltered} whose values
18761d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * satisfy a predicate. The returned multimap is a live view of
18771d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code unfiltered}; changes to one affect the other.
18781d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
18791d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The resulting multimap's views have iterators that don't support
18801d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code remove()}, but all other methods are supported by the multimap and
18811d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * its views. When adding a value that doesn't satisfy the predicate, the
18827dd252788645e940eada959bdde927426e2531c9Paul Duffin   * multimap's {@code put()}, {@code putAll()}, and {@code replaceValues()}
18837dd252788645e940eada959bdde927426e2531c9Paul Duffin   * methods throw an {@link IllegalArgumentException}.
18841d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
18851d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>When methods such as {@code removeAll()} and {@code clear()} are called on
18861d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * the filtered multimap or its views, only mappings whose value satisfy the
18871d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * filter will be removed from the underlying multimap.
18881d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
18891d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The returned multimap isn't threadsafe or serializable, even if
18901d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code unfiltered} is.
18911d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
18921d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Many of the filtered multimap's methods, such as {@code size()}, iterate
18931d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * across every key/value mapping in the underlying multimap and determine
18941d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * which satisfy the filter. When a live view is <i>not</i> needed, it may be
18951d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * faster to copy the filtered multimap and use the copy.
18961d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
18971d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p><b>Warning:</b> {@code valuePredicate} must be <i>consistent with
18981d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * equals</i>, as documented at {@link Predicate#apply}. Do not provide a
18991d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * predicate such as {@code Predicates.instanceOf(ArrayList.class)}, which is
19001d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * inconsistent with equals.
19011d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
19021d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @since 11.0
19031d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
19040888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> Multimap<K, V> filterValues(
19050888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Multimap<K, V> unfiltered, final Predicate<? super V> valuePredicate) {
19060888a09821a98ac0680fad765217302858e70fa4Paul Duffin    return filterEntries(unfiltered, Maps.<V>valuePredicateOnEntries(valuePredicate));
19070888a09821a98ac0680fad765217302858e70fa4Paul Duffin  }
19080888a09821a98ac0680fad765217302858e70fa4Paul Duffin
19090888a09821a98ac0680fad765217302858e70fa4Paul Duffin  /**
19100888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * Returns a multimap containing the mappings in {@code unfiltered} whose values
19110888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * satisfy a predicate. The returned multimap is a live view of
19120888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * {@code unfiltered}; changes to one affect the other.
19130888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
19140888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>The resulting multimap's views have iterators that don't support
19150888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * {@code remove()}, but all other methods are supported by the multimap and
19160888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * its views. When adding a value that doesn't satisfy the predicate, the
19170888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * multimap's {@code put()}, {@code putAll()}, and {@code replaceValues()}
19180888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * methods throw an {@link IllegalArgumentException}.
19190888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
19200888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>When methods such as {@code removeAll()} and {@code clear()} are called on
19210888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * the filtered multimap or its views, only mappings whose value satisfy the
19220888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * filter will be removed from the underlying multimap.
19230888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
19240888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>The returned multimap isn't threadsafe or serializable, even if
19250888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * {@code unfiltered} is.
19260888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
19270888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>Many of the filtered multimap's methods, such as {@code size()}, iterate
19280888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * across every key/value mapping in the underlying multimap and determine
19290888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * which satisfy the filter. When a live view is <i>not</i> needed, it may be
19300888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * faster to copy the filtered multimap and use the copy.
19310888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
19320888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p><b>Warning:</b> {@code valuePredicate} must be <i>consistent with
19330888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * equals</i>, as documented at {@link Predicate#apply}. Do not provide a
19340888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * predicate such as {@code Predicates.instanceOf(ArrayList.class)}, which is
19350888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * inconsistent with equals.
19360888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
19370888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * @since 14.0
19380888a09821a98ac0680fad765217302858e70fa4Paul Duffin   */
19390888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> SetMultimap<K, V> filterValues(
19400888a09821a98ac0680fad765217302858e70fa4Paul Duffin      SetMultimap<K, V> unfiltered, final Predicate<? super V> valuePredicate) {
19410888a09821a98ac0680fad765217302858e70fa4Paul Duffin    return filterEntries(unfiltered, Maps.<V>valuePredicateOnEntries(valuePredicate));
19421d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
19431d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
19441d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
19451d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Returns a multimap containing the mappings in {@code unfiltered} that
19461d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * satisfy a predicate. The returned multimap is a live view of
19471d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code unfiltered}; changes to one affect the other.
19481d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
19491d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The resulting multimap's views have iterators that don't support
19501d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code remove()}, but all other methods are supported by the multimap and
19511d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * its views. When adding a key/value pair that doesn't satisfy the predicate,
19527dd252788645e940eada959bdde927426e2531c9Paul Duffin   * multimap's {@code put()}, {@code putAll()}, and {@code replaceValues()}
19537dd252788645e940eada959bdde927426e2531c9Paul Duffin   * methods throw an {@link IllegalArgumentException}.
19541d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
19551d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>When methods such as {@code removeAll()} and {@code clear()} are called on
19561d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * the filtered multimap or its views, only mappings whose keys satisfy the
19571d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * filter will be removed from the underlying multimap.
19581d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
19591d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>The returned multimap isn't threadsafe or serializable, even if
19601d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * {@code unfiltered} is.
19611d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
19621d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p>Many of the filtered multimap's methods, such as {@code size()}, iterate
19631d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * across every key/value mapping in the underlying multimap and determine
19641d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * which satisfy the filter. When a live view is <i>not</i> needed, it may be
19651d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * faster to copy the filtered multimap and use the copy.
19661d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
19671d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * <p><b>Warning:</b> {@code entryPredicate} must be <i>consistent with
19681d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * equals</i>, as documented at {@link Predicate#apply}.
19691d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   *
19701d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * @since 11.0
19711d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
19720888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> Multimap<K, V> filterEntries(
19730888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Multimap<K, V> unfiltered, Predicate<? super Entry<K, V>> entryPredicate) {
19741d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert    checkNotNull(entryPredicate);
19750888a09821a98ac0680fad765217302858e70fa4Paul Duffin    if (unfiltered instanceof SetMultimap) {
19760888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return filterEntries((SetMultimap<K, V>) unfiltered, entryPredicate);
19770888a09821a98ac0680fad765217302858e70fa4Paul Duffin    }
19780888a09821a98ac0680fad765217302858e70fa4Paul Duffin    return (unfiltered instanceof FilteredMultimap)
19790888a09821a98ac0680fad765217302858e70fa4Paul Duffin        ? filterFiltered((FilteredMultimap<K, V>) unfiltered, entryPredicate)
19800888a09821a98ac0680fad765217302858e70fa4Paul Duffin        : new FilteredEntryMultimap<K, V>(checkNotNull(unfiltered), entryPredicate);
19810888a09821a98ac0680fad765217302858e70fa4Paul Duffin  }
19820888a09821a98ac0680fad765217302858e70fa4Paul Duffin
19830888a09821a98ac0680fad765217302858e70fa4Paul Duffin  /**
19840888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * Returns a multimap containing the mappings in {@code unfiltered} that
19850888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * satisfy a predicate. The returned multimap is a live view of
19860888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * {@code unfiltered}; changes to one affect the other.
19870888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
19880888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>The resulting multimap's views have iterators that don't support
19890888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * {@code remove()}, but all other methods are supported by the multimap and
19900888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * its views. When adding a key/value pair that doesn't satisfy the predicate,
19910888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * multimap's {@code put()}, {@code putAll()}, and {@code replaceValues()}
19920888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * methods throw an {@link IllegalArgumentException}.
19930888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
19940888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>When methods such as {@code removeAll()} and {@code clear()} are called on
19950888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * the filtered multimap or its views, only mappings whose keys satisfy the
19960888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * filter will be removed from the underlying multimap.
19970888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
19980888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>The returned multimap isn't threadsafe or serializable, even if
19990888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * {@code unfiltered} is.
20000888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
20010888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p>Many of the filtered multimap's methods, such as {@code size()}, iterate
20020888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * across every key/value mapping in the underlying multimap and determine
20030888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * which satisfy the filter. When a live view is <i>not</i> needed, it may be
20040888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * faster to copy the filtered multimap and use the copy.
20050888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
20060888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * <p><b>Warning:</b> {@code entryPredicate} must be <i>consistent with
20070888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * equals</i>, as documented at {@link Predicate#apply}.
20080888a09821a98ac0680fad765217302858e70fa4Paul Duffin   *
20090888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * @since 14.0
20100888a09821a98ac0680fad765217302858e70fa4Paul Duffin   */
20110888a09821a98ac0680fad765217302858e70fa4Paul Duffin  public static <K, V> SetMultimap<K, V> filterEntries(
20120888a09821a98ac0680fad765217302858e70fa4Paul Duffin      SetMultimap<K, V> unfiltered, Predicate<? super Entry<K, V>> entryPredicate) {
20130888a09821a98ac0680fad765217302858e70fa4Paul Duffin    checkNotNull(entryPredicate);
20140888a09821a98ac0680fad765217302858e70fa4Paul Duffin    return (unfiltered instanceof FilteredSetMultimap)
20150888a09821a98ac0680fad765217302858e70fa4Paul Duffin        ? filterFiltered((FilteredSetMultimap<K, V>) unfiltered, entryPredicate)
20160888a09821a98ac0680fad765217302858e70fa4Paul Duffin        : new FilteredEntrySetMultimap<K, V>(checkNotNull(unfiltered), entryPredicate);
20171d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
20181d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
20191d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  /**
20201d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * Support removal operations when filtering a filtered multimap. Since a
20211d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * filtered multimap has iterators that don't support remove, passing one to
20227dd252788645e940eada959bdde927426e2531c9Paul Duffin   * the FilteredEntryMultimap constructor would lead to a multimap whose removal
20231d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * operations would fail. This method combines the predicates to avoid that
20241d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   * problem.
20251d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert   */
20267dd252788645e940eada959bdde927426e2531c9Paul Duffin  private static <K, V> Multimap<K, V> filterFiltered(FilteredMultimap<K, V> multimap,
20271d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert      Predicate<? super Entry<K, V>> entryPredicate) {
20280888a09821a98ac0680fad765217302858e70fa4Paul Duffin    Predicate<Entry<K, V>> predicate
20290888a09821a98ac0680fad765217302858e70fa4Paul Duffin        = Predicates.and(multimap.entryPredicate(), entryPredicate);
20300888a09821a98ac0680fad765217302858e70fa4Paul Duffin    return new FilteredEntryMultimap<K, V>(multimap.unfiltered(), predicate);
20310888a09821a98ac0680fad765217302858e70fa4Paul Duffin  }
20320888a09821a98ac0680fad765217302858e70fa4Paul Duffin
20330888a09821a98ac0680fad765217302858e70fa4Paul Duffin  /**
20340888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * Support removal operations when filtering a filtered multimap. Since a filtered multimap has
20350888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * iterators that don't support remove, passing one to the FilteredEntryMultimap constructor would
20360888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * lead to a multimap whose removal operations would fail. This method combines the predicates to
20370888a09821a98ac0680fad765217302858e70fa4Paul Duffin   * avoid that problem.
20380888a09821a98ac0680fad765217302858e70fa4Paul Duffin   */
20390888a09821a98ac0680fad765217302858e70fa4Paul Duffin  private static <K, V> SetMultimap<K, V> filterFiltered(
20400888a09821a98ac0680fad765217302858e70fa4Paul Duffin      FilteredSetMultimap<K, V> multimap,
20410888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Predicate<? super Entry<K, V>> entryPredicate) {
20420888a09821a98ac0680fad765217302858e70fa4Paul Duffin    Predicate<Entry<K, V>> predicate
20430888a09821a98ac0680fad765217302858e70fa4Paul Duffin        = Predicates.and(multimap.entryPredicate(), entryPredicate);
20440888a09821a98ac0680fad765217302858e70fa4Paul Duffin    return new FilteredEntrySetMultimap<K, V>(multimap.unfiltered(), predicate);
20450888a09821a98ac0680fad765217302858e70fa4Paul Duffin  }
20460888a09821a98ac0680fad765217302858e70fa4Paul Duffin
20470888a09821a98ac0680fad765217302858e70fa4Paul Duffin  static boolean equalsImpl(Multimap<?, ?> multimap, @Nullable Object object) {
20480888a09821a98ac0680fad765217302858e70fa4Paul Duffin    if (object == multimap) {
20490888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return true;
20500888a09821a98ac0680fad765217302858e70fa4Paul Duffin    }
20510888a09821a98ac0680fad765217302858e70fa4Paul Duffin    if (object instanceof Multimap) {
20520888a09821a98ac0680fad765217302858e70fa4Paul Duffin      Multimap<?, ?> that = (Multimap<?, ?>) object;
20530888a09821a98ac0680fad765217302858e70fa4Paul Duffin      return multimap.asMap().equals(that.asMap());
20540888a09821a98ac0680fad765217302858e70fa4Paul Duffin    }
20550888a09821a98ac0680fad765217302858e70fa4Paul Duffin    return false;
20561d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert  }
20571d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert
20580888a09821a98ac0680fad765217302858e70fa4Paul Duffin  // TODO(jlevy): Create methods that filter a SortedSetMultimap.
20591d580d0f6ee4f21eb309ba7b509d2c6d671c4044Bjorn Bringert}
2060