alvinalexander.com | career | drupal | java | mac | mysql | perl | scala | uml | unix  

Java example source code file (MultimapsTest.java)

This example Java source code file (MultimapsTest.java) is included in the alvinalexander.com "Java Source Code Warehouse" project. The intent of this project is to help you "Learn Java by Example" TM.

Learn more about this Java project at its project page.

Java - Java tags/keywords

annotation, collection, countingsupplier, expected, gwtincompatible, illegalargumentexception, integer, listmultimap, map, multimap, override, serializabletester, setmultimap, string, unsupportedoperationexception, util

The MultimapsTest.java Java example source code

/*
 * Copyright (C) 2007 The Guava Authors
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.google.common.collect;

import static com.google.common.base.Preconditions.checkArgument;
import static com.google.common.collect.Maps.immutableEntry;
import static com.google.common.collect.Sets.newHashSet;
import static com.google.common.collect.testing.Helpers.nefariousMapEntry;
import static com.google.common.collect.testing.IteratorFeature.MODIFIABLE;
import static com.google.common.truth.Truth.assertThat;
import static java.util.Arrays.asList;

import com.google.common.annotations.GwtCompatible;
import com.google.common.annotations.GwtIncompatible;
import com.google.common.base.Function;
import com.google.common.base.Functions;
import com.google.common.base.Predicates;
import com.google.common.base.Supplier;
import com.google.common.collect.Maps.EntryTransformer;
import com.google.common.collect.testing.IteratorTester;
import com.google.common.collect.testing.google.UnmodifiableCollectionTests;
import com.google.common.testing.NullPointerTester;
import com.google.common.testing.SerializableTester;

import junit.framework.TestCase;

import java.io.Serializable;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.Comparator;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Queue;
import java.util.RandomAccess;
import java.util.Set;
import java.util.SortedMap;
import java.util.SortedSet;
import java.util.TreeSet;

import javax.annotation.Nullable;

/**
 * Unit test for {@code Multimaps}.
 *
 * @author Jared Levy
 */
@GwtCompatible(emulated = true)
public class MultimapsTest extends TestCase {

  private static final Comparator<Integer> INT_COMPARATOR =
      Ordering.<Integer>natural().reverse().nullsFirst();

  @SuppressWarnings("deprecation")
  public void testUnmodifiableListMultimapShortCircuit() {
    ListMultimap<String, Integer> mod = ArrayListMultimap.create();
    ListMultimap<String, Integer> unmod = Multimaps.unmodifiableListMultimap(mod);
    assertNotSame(mod, unmod);
    assertSame(unmod, Multimaps.unmodifiableListMultimap(unmod));
    ImmutableListMultimap<String, Integer> immutable =
        ImmutableListMultimap.of("a", 1, "b", 2, "a", 3);
    assertSame(immutable, Multimaps.unmodifiableListMultimap(immutable));
    assertSame(
        immutable, Multimaps.unmodifiableListMultimap((ListMultimap<String, Integer>) immutable));
  }

  @SuppressWarnings("deprecation")
  public void testUnmodifiableSetMultimapShortCircuit() {
    SetMultimap<String, Integer> mod = HashMultimap.create();
    SetMultimap<String, Integer> unmod = Multimaps.unmodifiableSetMultimap(mod);
    assertNotSame(mod, unmod);
    assertSame(unmod, Multimaps.unmodifiableSetMultimap(unmod));
    ImmutableSetMultimap<String, Integer> immutable =
        ImmutableSetMultimap.of("a", 1, "b", 2, "a", 3);
    assertSame(immutable, Multimaps.unmodifiableSetMultimap(immutable));
    assertSame(
        immutable, Multimaps.unmodifiableSetMultimap((SetMultimap<String, Integer>) immutable));
  }

  @SuppressWarnings("deprecation")
  public void testUnmodifiableMultimapShortCircuit() {
    Multimap<String, Integer> mod = HashMultimap.create();
    Multimap<String, Integer> unmod = Multimaps.unmodifiableMultimap(mod);
    assertNotSame(mod, unmod);
    assertSame(unmod, Multimaps.unmodifiableMultimap(unmod));
    ImmutableMultimap<String, Integer> immutable = ImmutableMultimap.of("a", 1, "b", 2, "a", 3);
    assertSame(immutable, Multimaps.unmodifiableMultimap(immutable));
    assertSame(immutable, Multimaps.unmodifiableMultimap((Multimap<String, Integer>) immutable));
  }

  @GwtIncompatible // slow (~10s)
  public void testUnmodifiableArrayListMultimap() {
    checkUnmodifiableMultimap(
        ArrayListMultimap.<String, Integer>create(), true);
  }

  @GwtIncompatible // SerializableTester
  public void testSerializingUnmodifiableArrayListMultimap() {
    Multimap<String, Integer> unmodifiable =
        prepareUnmodifiableTests(ArrayListMultimap.<String, Integer>create(), true, null, null);
    SerializableTester.reserializeAndAssert(unmodifiable);
  }

  public void testUnmodifiableArrayListMultimapRandomAccess() {
    ListMultimap<String, Integer> delegate = ArrayListMultimap.create();
    delegate.put("foo", 1);
    delegate.put("foo", 3);
    ListMultimap<String, Integer> multimap
        = Multimaps.unmodifiableListMultimap(delegate);
    assertTrue(multimap.get("foo") instanceof RandomAccess);
    assertTrue(multimap.get("bar") instanceof RandomAccess);
  }

  public void testUnmodifiableLinkedListMultimapRandomAccess() {
    ListMultimap<String, Integer> delegate = LinkedListMultimap.create();
    delegate.put("foo", 1);
    delegate.put("foo", 3);
    ListMultimap<String, Integer> multimap = Multimaps.unmodifiableListMultimap(delegate);
    assertThat(multimap.get("foo")).isNotInstanceOf(RandomAccess.class);
    assertThat(multimap.get("bar")).isNotInstanceOf(RandomAccess.class);
  }

  @GwtIncompatible // slow (~10s)
  public void testUnmodifiableHashMultimap() {
    checkUnmodifiableMultimap(HashMultimap.<String, Integer>create(), false);
  }

  @GwtIncompatible // SerializableTester
  public void testSerializingUnmodifiableHashMultimap() {
    Multimap<String, Integer> unmodifiable =
        prepareUnmodifiableTests(HashMultimap.<String, Integer>create(), false, null, null);
    SerializableTester.reserializeAndAssert(unmodifiable);
  }

  @GwtIncompatible // slow (~10s)
  public void testUnmodifiableTreeMultimap() {
    checkUnmodifiableMultimap(
        TreeMultimap.<String, Integer>create(), false, "null", 42);
  }

  @GwtIncompatible // SerializableTester
  public void testSerializingUnmodifiableTreeMultimap() {
    Multimap<String, Integer> unmodifiable =
        prepareUnmodifiableTests(TreeMultimap.<String, Integer>create(), false, "null", 42);
    SerializableTester.reserializeAndAssert(unmodifiable);
  }

  @GwtIncompatible // slow (~10s)
  public void testUnmodifiableSynchronizedArrayListMultimap() {
    checkUnmodifiableMultimap(Multimaps.synchronizedListMultimap(
        ArrayListMultimap.<String, Integer>create()), true);
  }

  @GwtIncompatible // SerializableTester
  public void testSerializingUnmodifiableSynchronizedArrayListMultimap() {
    Multimap<String, Integer> unmodifiable =
        prepareUnmodifiableTests(Multimaps.synchronizedListMultimap(
          ArrayListMultimap.<String, Integer>create()), true, null, null);
    SerializableTester.reserializeAndAssert(unmodifiable);
  }

  @GwtIncompatible // slow (~10s)
  public void testUnmodifiableSynchronizedHashMultimap() {
    checkUnmodifiableMultimap(Multimaps.synchronizedSetMultimap(
        HashMultimap.<String, Integer>create()), false);
  }

  @GwtIncompatible // SerializableTester
  public void testSerializingUnmodifiableSynchronizedHashMultimap() {
    Multimap<String, Integer> unmodifiable =
        prepareUnmodifiableTests(Multimaps.synchronizedSetMultimap(
        HashMultimap.<String, Integer>create()), false, null, null);
    SerializableTester.reserializeAndAssert(unmodifiable);
  }

  @GwtIncompatible // slow (~10s)
  public void testUnmodifiableSynchronizedTreeMultimap() {
    TreeMultimap<String, Integer> delegate
        = TreeMultimap.create(Ordering.<String>natural(), INT_COMPARATOR);
    SortedSetMultimap<String, Integer> multimap
        = Multimaps.synchronizedSortedSetMultimap(delegate);
    checkUnmodifiableMultimap(multimap, false, "null", 42);
    assertSame(INT_COMPARATOR, multimap.valueComparator());
  }

  @GwtIncompatible // SerializableTester
  public void testSerializingUnmodifiableSynchronizedTreeMultimap() {
    TreeMultimap<String, Integer> delegate =
        TreeMultimap.create(Ordering.<String>natural(), INT_COMPARATOR);
    SortedSetMultimap<String, Integer> multimap =
        Multimaps.synchronizedSortedSetMultimap(delegate);
    Multimap<String, Integer> unmodifiable =
        prepareUnmodifiableTests(multimap, false, "null", 42);
    SerializableTester.reserializeAndAssert(unmodifiable);
    assertSame(INT_COMPARATOR, multimap.valueComparator());
  }

  public void testUnmodifiableMultimapIsView() {
    Multimap<String, Integer> mod = HashMultimap.create();
    Multimap<String, Integer> unmod = Multimaps.unmodifiableMultimap(mod);
    assertEquals(mod, unmod);
    mod.put("foo", 1);
    assertTrue(unmod.containsEntry("foo", 1));
    assertEquals(mod, unmod);
  }

  @SuppressWarnings("unchecked")
  public void testUnmodifiableMultimapEntries() {
    Multimap<String, Integer> mod = HashMultimap.create();
    Multimap<String, Integer> unmod = Multimaps.unmodifiableMultimap(mod);
    mod.put("foo", 1);
    Entry<String, Integer> entry = unmod.entries().iterator().next();
    try {
      entry.setValue(2);
      fail("UnsupportedOperationException expected");
    } catch (UnsupportedOperationException expected) {}
    entry = (Entry<String, Integer>) unmod.entries().toArray()[0];
    try {
      entry.setValue(2);
      fail("UnsupportedOperationException expected");
    } catch (UnsupportedOperationException expected) {}
    Entry<String, Integer>[] array
        = (Entry<String, Integer>[]) new Entry[2];
    assertSame(array, unmod.entries().toArray(array));
    try {
      array[0].setValue(2);
      fail("UnsupportedOperationException expected");
    } catch (UnsupportedOperationException expected) {}
    assertFalse(unmod.entries().contains(nefariousMapEntry("pwnd", 2)));
    assertFalse(unmod.keys().contains("pwnd"));
  }

  /**
   * The supplied multimap will be mutated and an unmodifiable instance used
   * in its stead. The multimap must support null keys and values.
   */
  private static void checkUnmodifiableMultimap(
      Multimap<String, Integer> multimap, boolean permitsDuplicates) {
    checkUnmodifiableMultimap(multimap, permitsDuplicates, null, null);
  }

  /**
   * The supplied multimap will be mutated and an unmodifiable instance used
   * in its stead. If the multimap does not support null keys or values,
   * alternatives may be specified for tests involving nulls.
   */
  private static void checkUnmodifiableMultimap(
      Multimap<String, Integer> multimap, boolean permitsDuplicates,
      @Nullable String nullKey, @Nullable Integer nullValue) {
    Multimap<String, Integer> unmodifiable =
        prepareUnmodifiableTests(multimap, permitsDuplicates, nullKey, nullValue);

    UnmodifiableCollectionTests.assertMultimapIsUnmodifiable(
        unmodifiable, "test", 123);

    assertUnmodifiableIterableInTandem(
        unmodifiable.keys(), multimap.keys());

    assertUnmodifiableIterableInTandem(
        unmodifiable.keySet(), multimap.keySet());

    assertUnmodifiableIterableInTandem(
        unmodifiable.entries(), multimap.entries());

    assertUnmodifiableIterableInTandem(
        unmodifiable.asMap().entrySet(), multimap.asMap().entrySet());

    assertEquals(multimap.toString(), unmodifiable.toString());
    assertEquals(multimap.hashCode(), unmodifiable.hashCode());
    assertEquals(multimap, unmodifiable);

    assertThat(unmodifiable.asMap().get("bar")).containsExactly(5, -1);
    assertNull(unmodifiable.asMap().get("missing"));

    assertThat(unmodifiable.entries()).isNotInstanceOf(Serializable.class);
  }

  /**
   * Prepares the multimap for unmodifiable tests, returning an unmodifiable view
   * of the map.
   */
  private static Multimap<String, Integer> prepareUnmodifiableTests(
      Multimap<String, Integer> multimap, boolean permitsDuplicates,
      @Nullable String nullKey, @Nullable Integer nullValue) {
    multimap.clear();
    multimap.put("foo", 1);
    multimap.put("foo", 2);
    multimap.put("foo", 3);
    multimap.put("bar", 5);
    multimap.put("bar", -1);
    multimap.put(nullKey, nullValue);
    multimap.put("foo", nullValue);
    multimap.put(nullKey, 5);
    multimap.put("foo", 2);

    if (permitsDuplicates) {
      assertEquals(9, multimap.size());
    } else {
      assertEquals(8, multimap.size());
    }

    Multimap<String, Integer> unmodifiable;
    if (multimap instanceof SortedSetMultimap) {
      unmodifiable = Multimaps.unmodifiableSortedSetMultimap(
          (SortedSetMultimap<String, Integer>) multimap);
    } else if (multimap instanceof SetMultimap) {
      unmodifiable = Multimaps.unmodifiableSetMultimap(
          (SetMultimap<String, Integer>) multimap);
    } else if (multimap instanceof ListMultimap) {
      unmodifiable = Multimaps.unmodifiableListMultimap(
          (ListMultimap<String, Integer>) multimap);
    } else {
      unmodifiable = Multimaps.unmodifiableMultimap(multimap);
    }
    return unmodifiable;
  }

  private static <T> void assertUnmodifiableIterableInTandem(
      Iterable<T> unmodifiable, Iterable modifiable) {
    UnmodifiableCollectionTests.assertIteratorIsUnmodifiable(
        unmodifiable.iterator());
    UnmodifiableCollectionTests.assertIteratorsInOrder(
        unmodifiable.iterator(), modifiable.iterator());
  }

  public void testInvertFrom() {
    ImmutableMultimap<Integer, String> empty = ImmutableMultimap.of();

    // typical usage example - sad that ArrayListMultimap.create() won't work
    Multimap<String, Integer> multimap = Multimaps.invertFrom(empty,
        ArrayListMultimap.<String, Integer>create());
    assertTrue(multimap.isEmpty());

    ImmutableMultimap<Integer, String> single
        = new ImmutableMultimap.Builder<Integer, String>()
            .put(1, "one")
            .put(2, "two")
            .build();

    // copy into existing multimap
    assertSame(multimap, Multimaps.invertFrom(single, multimap));

    ImmutableMultimap<String, Integer> expected
        = new ImmutableMultimap.Builder<String, Integer>()
        .put("one", 1)
        .put("two", 2)
        .build();

    assertEquals(expected, multimap);
  }

  public void testAsMap_multimap() {
    Multimap<String, Integer> multimap = Multimaps.newMultimap(
        new HashMap<String, Collection(), new QueueSupplier());
    Map<String, Collection map = Multimaps.asMap(multimap);
    assertSame(multimap.asMap(), map);
  }

  public void testAsMap_listMultimap() {
    ListMultimap<String, Integer> listMultimap = ArrayListMultimap.create();
    Map<String, List map = Multimaps.asMap(listMultimap);
    assertSame(listMultimap.asMap(), map);
  }

  public void testAsMap_setMultimap() {
    SetMultimap<String, Integer> setMultimap = LinkedHashMultimap.create();
    Map<String, Set map = Multimaps.asMap(setMultimap);
    assertSame(setMultimap.asMap(), map);
  }

  public void testAsMap_sortedSetMultimap() {
    SortedSetMultimap<String, Integer> sortedSetMultimap =
        TreeMultimap.create();
    Map<String, SortedSet map = Multimaps.asMap(sortedSetMultimap);
    assertSame(sortedSetMultimap.asMap(), map);
  }

  public void testForMap() {
    Map<String, Integer> map = Maps.newHashMap();
    map.put("foo", 1);
    map.put("bar", 2);
    Multimap<String, Integer> multimap = HashMultimap.create();
    multimap.put("foo", 1);
    multimap.put("bar", 2);
    Multimap<String, Integer> multimapView = Multimaps.forMap(map);
    assertTrue(multimap.equals(multimapView));
    assertTrue(multimapView.equals(multimap));
    assertTrue(multimapView.equals(multimapView));
    assertFalse(multimapView.equals(map));
    Multimap<String, Integer> multimap2 = HashMultimap.create();
    multimap2.put("foo", 1);
    assertFalse(multimapView.equals(multimap2));
    multimap2.put("bar", 1);
    assertFalse(multimapView.equals(multimap2));
    ListMultimap<String, Integer> listMultimap
        = new ImmutableListMultimap.Builder<String, Integer>()
            .put("foo", 1).put("bar", 2).build();
    assertFalse("SetMultimap equals ListMultimap",
        multimapView.equals(listMultimap));
    assertEquals(multimap.toString(), multimapView.toString());
    assertEquals(multimap.hashCode(), multimapView.hashCode());
    assertEquals(multimap.size(), multimapView.size());
    assertTrue(multimapView.containsKey("foo"));
    assertTrue(multimapView.containsValue(1));
    assertTrue(multimapView.containsEntry("bar", 2));
    assertEquals(Collections.singleton(1), multimapView.get("foo"));
    assertEquals(Collections.singleton(2), multimapView.get("bar"));
    try {
      multimapView.put("baz", 3);
      fail("UnsupportedOperationException expected");
    } catch (UnsupportedOperationException expected) {}
    try {
      multimapView.putAll("baz", Collections.singleton(3));
      fail("UnsupportedOperationException expected");
    } catch (UnsupportedOperationException expected) {}
    try {
      multimapView.putAll(multimap);
      fail("UnsupportedOperationException expected");
    } catch (UnsupportedOperationException expected) {}
    try {
      multimapView.replaceValues("foo", Collections.<Integer>emptySet());
      fail("UnsupportedOperationException expected");
    } catch (UnsupportedOperationException expected) {}
    multimapView.remove("bar", 2);
    assertFalse(multimapView.containsKey("bar"));
    assertFalse(map.containsKey("bar"));
    assertEquals(map.keySet(), multimapView.keySet());
    assertEquals(map.keySet(), multimapView.keys().elementSet());
    assertThat(multimapView.keys()).contains("foo");
    assertThat(multimapView.values()).contains(1);
    assertThat(multimapView.entries()).contains(Maps.immutableEntry("foo", 1));
    assertThat(multimapView.asMap().entrySet())
        .contains(Maps.immutableEntry("foo", (Collection<Integer>) Collections.singleton(1)));
    multimapView.clear();
    assertFalse(multimapView.containsKey("foo"));
    assertFalse(map.containsKey("foo"));
    assertTrue(map.isEmpty());
    assertTrue(multimapView.isEmpty());
    multimap.clear();
    assertEquals(multimap.toString(), multimapView.toString());
    assertEquals(multimap.hashCode(), multimapView.hashCode());
    assertEquals(multimap.size(), multimapView.size());
    assertEquals(multimapView, ArrayListMultimap.create());
  }

  @GwtIncompatible // SerializableTester
  public void testForMapSerialization() {
    Map<String, Integer> map = Maps.newHashMap();
    map.put("foo", 1);
    map.put("bar", 2);
    Multimap<String, Integer> multimapView = Multimaps.forMap(map);
    SerializableTester.reserializeAndAssert(multimapView);
  }

  public void testForMapRemoveAll() {
    Map<String, Integer> map = Maps.newHashMap();
    map.put("foo", 1);
    map.put("bar", 2);
    map.put("cow", 3);
    Multimap<String, Integer> multimap = Multimaps.forMap(map);
    assertEquals(3, multimap.size());
    assertEquals(Collections.emptySet(), multimap.removeAll("dog"));
    assertEquals(3, multimap.size());
    assertTrue(multimap.containsKey("bar"));
    assertEquals(Collections.singleton(2), multimap.removeAll("bar"));
    assertEquals(2, multimap.size());
    assertFalse(multimap.containsKey("bar"));
  }

  public void testForMapAsMap() {
    Map<String, Integer> map = Maps.newHashMap();
    map.put("foo", 1);
    map.put("bar", 2);
    Map<String, Collection asMap = Multimaps.forMap(map).asMap();
    assertEquals(Collections.singleton(1), asMap.get("foo"));
    assertNull(asMap.get("cow"));
    assertTrue(asMap.containsKey("foo"));
    assertFalse(asMap.containsKey("cow"));

    Set<Entry> entries = asMap.entrySet();
    assertFalse(entries.contains((Object) 4.5));
    assertFalse(entries.remove((Object) 4.5));
    assertFalse(entries.contains(Maps.immutableEntry("foo",
        Collections.singletonList(1))));
    assertFalse(entries.remove(Maps.immutableEntry("foo",
        Collections.singletonList(1))));
    assertFalse(entries.contains(Maps.immutableEntry("foo",
        Sets.newLinkedHashSet(asList(1, 2)))));
    assertFalse(entries.remove(Maps.immutableEntry("foo",
        Sets.newLinkedHashSet(asList(1, 2)))));
    assertFalse(entries.contains(Maps.immutableEntry("foo",
        Collections.singleton(2))));
    assertFalse(entries.remove(Maps.immutableEntry("foo",
        Collections.singleton(2))));
    assertTrue(map.containsKey("foo"));
    assertTrue(entries.contains(Maps.immutableEntry("foo",
        Collections.singleton(1))));
    assertTrue(entries.remove(Maps.immutableEntry("foo",
        Collections.singleton(1))));
    assertFalse(map.containsKey("foo"));
  }

  public void testForMapGetIteration() {
    IteratorTester<Integer> tester =
        new IteratorTester<Integer>(4, MODIFIABLE, newHashSet(1),
            IteratorTester.KnownOrder.KNOWN_ORDER) {
          private Multimap<String, Integer> multimap;

          @Override protected Iterator<Integer> newTargetIterator() {
            Map<String, Integer> map = Maps.newHashMap();
            map.put("foo", 1);
            map.put("bar", 2);
            multimap = Multimaps.forMap(map);
            return multimap.get("foo").iterator();
          }

          @Override protected void verify(List<Integer> elements) {
            assertEquals(newHashSet(elements), multimap.get("foo"));
          }
        };

    tester.test();
  }

  private enum Color {BLUE, RED, YELLOW, GREEN}

  private abstract static class CountingSupplier<E>
      implements Supplier<E>, Serializable {
    int count;

    abstract E getImpl();

    @Override
    public E get() {
      count++;
      return getImpl();
    }
  }

  private static class QueueSupplier extends CountingSupplier<Queue {
    @Override public Queue<Integer> getImpl() {
      return new LinkedList<Integer>();
    }
    private static final long serialVersionUID = 0;
  }

  public void testNewMultimapWithCollectionRejectingNegativeElements() {
    CountingSupplier<Set factory = new SetSupplier() {
      @Override
      public Set<Integer> getImpl() {
        final Set<Integer> backing = super.getImpl();
        return new ForwardingSet<Integer>() {
          @Override
          protected Set<Integer> delegate() {
            return backing;
          }

          @Override
          public boolean add(Integer element) {
            checkArgument(element >= 0);
            return super.add(element);
          }

          @Override
          public boolean addAll(Collection<? extends Integer> collection) {
            return standardAddAll(collection);
          }
        };
      }
    };

    Map<Color, Collection map = Maps.newEnumMap(Color.class);
    Multimap<Color, Integer> multimap = Multimaps.newMultimap(map, factory);
    try {
      multimap.put(Color.BLUE, -1);
      fail("Expected IllegalArgumentException");
    } catch (IllegalArgumentException expected) {
      // expected
    }
    multimap.put(Color.RED, 1);
    multimap.put(Color.BLUE, 2);
    try {
      multimap.put(Color.GREEN, -1);
      fail("Expected IllegalArgumentException");
    } catch (IllegalArgumentException expected) {
      // expected
    }
    assertThat(multimap.entries()).containsExactly(
        Maps.immutableEntry(Color.RED, 1),
        Maps.immutableEntry(Color.BLUE, 2));
  }

  public void testNewMultimap() {
    // The ubiquitous EnumArrayBlockingQueueMultimap
    CountingSupplier<Queue factory = new QueueSupplier();

    Map<Color, Collection map = Maps.newEnumMap(Color.class);
    Multimap<Color, Integer> multimap = Multimaps.newMultimap(map, factory);
    assertEquals(0, factory.count);
    multimap.putAll(Color.BLUE, asList(3, 1, 4));
    assertEquals(1, factory.count);
    multimap.putAll(Color.RED, asList(2, 7, 1, 8));
    assertEquals(2, factory.count);
    assertEquals("[3, 1, 4]", multimap.get(Color.BLUE).toString());

    Multimap<Color, Integer> ummodifiable =
        Multimaps.unmodifiableMultimap(multimap);
    assertEquals("[3, 1, 4]", ummodifiable.get(Color.BLUE).toString());

    Collection<Integer> collection = multimap.get(Color.BLUE);
    assertEquals(collection, collection);

    assertThat(multimap.keySet()).isNotInstanceOf(SortedSet.class);
    assertThat(multimap.asMap()).isNotInstanceOf(SortedMap.class);
  }

  @GwtIncompatible // SerializableTester
  public void testNewMultimapSerialization() {
    CountingSupplier<Queue factory = new QueueSupplier();
    Map<Color, Collection map = Maps.newEnumMap(Color.class);
    Multimap<Color, Integer> multimap = Multimaps.newMultimap(map, factory);
    multimap.putAll(Color.BLUE, asList(3, 1, 4));
    multimap.putAll(Color.RED, asList(2, 7, 1, 8));
    SerializableTester.reserializeAndAssert(multimap);
  }

  private static class ListSupplier extends
      CountingSupplier<LinkedList {
    @Override public LinkedList<Integer> getImpl() {
      return new LinkedList<Integer>();
    }
    private static final long serialVersionUID = 0;
  }

  public void testNewListMultimap() {
    CountingSupplier<LinkedList factory = new ListSupplier();
    Map<Color, Collection map = Maps.newTreeMap();
    ListMultimap<Color, Integer> multimap =
        Multimaps.newListMultimap(map, factory);
    assertEquals(0, factory.count);
    multimap.putAll(Color.BLUE, asList(3, 1, 4, 1));
    assertEquals(1, factory.count);
    multimap.putAll(Color.RED, asList(2, 7, 1, 8));
    assertEquals(2, factory.count);
    assertEquals("{BLUE=[3, 1, 4, 1], RED=[2, 7, 1, 8]}", multimap.toString());
    assertThat(multimap.get(Color.BLUE)).isNotInstanceOf(RandomAccess.class);

    assertTrue(multimap.keySet() instanceof SortedSet);
    assertTrue(multimap.asMap() instanceof SortedMap);
  }

  @GwtIncompatible // SerializableTester
  public void testNewListMultimapSerialization() {
    CountingSupplier<LinkedList factory = new ListSupplier();
    Map<Color, Collection map = Maps.newTreeMap();
    ListMultimap<Color, Integer> multimap = Multimaps.newListMultimap(map, factory);
    multimap.putAll(Color.BLUE, asList(3, 1, 4, 1));
    multimap.putAll(Color.RED, asList(2, 7, 1, 8));
    SerializableTester.reserializeAndAssert(multimap);
  }

  private static class SetSupplier extends CountingSupplier<Set {
    @Override public Set<Integer> getImpl() {
      return new HashSet<Integer>(4);
    }
    private static final long serialVersionUID = 0;
  }

  public void testNewSetMultimap() {
    CountingSupplier<Set factory = new SetSupplier();
    Map<Color, Collection map = Maps.newHashMap();
    SetMultimap<Color, Integer> multimap =
        Multimaps.newSetMultimap(map, factory);
    assertEquals(0, factory.count);
    multimap.putAll(Color.BLUE, asList(3, 1, 4));
    assertEquals(1, factory.count);
    multimap.putAll(Color.RED, asList(2, 7, 1, 8));
    assertEquals(2, factory.count);
    assertEquals(Sets.newHashSet(4, 3, 1), multimap.get(Color.BLUE));
  }

  @GwtIncompatible // SerializableTester
  public void testNewSetMultimapSerialization() {
    CountingSupplier<Set factory = new SetSupplier();
    Map<Color, Collection map = Maps.newHashMap();
    SetMultimap<Color, Integer> multimap = Multimaps.newSetMultimap(map, factory);
    multimap.putAll(Color.BLUE, asList(3, 1, 4));
    multimap.putAll(Color.RED, asList(2, 7, 1, 8));
    SerializableTester.reserializeAndAssert(multimap);
  }

  private static class SortedSetSupplier extends
      CountingSupplier<TreeSet {
    @Override public TreeSet<Integer> getImpl() {
      return Sets.newTreeSet(INT_COMPARATOR);
    }
    private static final long serialVersionUID = 0;
  }

  public void testNewSortedSetMultimap() {
    CountingSupplier<TreeSet factory = new SortedSetSupplier();
    Map<Color, Collection map = Maps.newEnumMap(Color.class);
    SortedSetMultimap<Color, Integer> multimap =
        Multimaps.newSortedSetMultimap(map, factory);
    // newSortedSetMultimap calls the factory once to determine the comparator.
    assertEquals(1, factory.count);
    multimap.putAll(Color.BLUE, asList(3, 1, 4));
    assertEquals(2, factory.count);
    multimap.putAll(Color.RED, asList(2, 7, 1, 8));
    assertEquals(3, factory.count);
    assertEquals("[4, 3, 1]", multimap.get(Color.BLUE).toString());
    assertEquals(INT_COMPARATOR, multimap.valueComparator());
  }

  @GwtIncompatible // SerializableTester
  public void testNewSortedSetMultimapSerialization() {
    CountingSupplier<TreeSet factory = new SortedSetSupplier();
    Map<Color, Collection map = Maps.newEnumMap(Color.class);
    SortedSetMultimap<Color, Integer> multimap = Multimaps.newSortedSetMultimap(map, factory);
    multimap.putAll(Color.BLUE, asList(3, 1, 4));
    multimap.putAll(Color.RED, asList(2, 7, 1, 8));
    SerializableTester.reserializeAndAssert(multimap);
    assertEquals(INT_COMPARATOR, multimap.valueComparator());
  }

  public void testIndex() {
    final Multimap<String, Object> stringToObject =
        new ImmutableMultimap.Builder<String, Object>()
            .put("1", 1)
            .put("1", 1L)
            .put("1", "1")
            .put("2", 2)
            .put("2", 2L)
            .build();

    ImmutableMultimap<String, Object> outputMap =
        Multimaps.index(stringToObject.values(),
            Functions.toStringFunction());
    assertEquals(stringToObject, outputMap);
  }

  public void testIndexIterator() {
    final Multimap<String, Object> stringToObject =
        new ImmutableMultimap.Builder<String, Object>()
            .put("1", 1)
            .put("1", 1L)
            .put("1", "1")
            .put("2", 2)
            .put("2", 2L)
            .build();

    ImmutableMultimap<String, Object> outputMap =
        Multimaps.index(stringToObject.values().iterator(),
            Functions.toStringFunction());
    assertEquals(stringToObject, outputMap);
  }

  public void testIndex_ordering() {
    final Multimap<Integer, String> expectedIndex =
        new ImmutableListMultimap.Builder<Integer, String>()
            .put(4, "Inky")
            .put(6, "Blinky")
            .put(5, "Pinky")
            .put(5, "Pinky")
            .put(5, "Clyde")
            .build();

    final List<String> badGuys =
        Arrays.asList("Inky", "Blinky", "Pinky", "Pinky", "Clyde");
    final Function<String, Integer> stringLengthFunction =
        new Function<String, Integer>() {
          @Override
          public Integer apply(String input) {
            return input.length();
          }
        };

    Multimap<Integer, String> index =
        Multimaps.index(badGuys, stringLengthFunction);

    assertEquals(expectedIndex, index);
  }

  public void testIndex_nullValue() {
    List<Integer> values = Arrays.asList(1, null);
    try {
      Multimaps.index(values, Functions.identity());
      fail();
    } catch (NullPointerException expected) {
    }
  }

  public void testIndex_nullKey() {
    List<Integer> values = Arrays.asList(1, 2);
    try {
      Multimaps.index(values, Functions.constant(null));
      fail();
    } catch (NullPointerException expected) {
    }
  }

  @GwtIncompatible(value = "untested")
  public void testTransformValues() {
    SetMultimap<String, Integer> multimap =
        ImmutableSetMultimap.of("a", 2, "b", -3, "b", 3, "a", 4, "c", 6);
    Function<Integer, Integer> square = new Function() {
      @Override
      public Integer apply(Integer in) {
        return in * in;
      }
    };
    Multimap<String, Integer> transformed = Multimaps.transformValues(multimap, square);
    assertThat(transformed.entries()).containsExactly(immutableEntry("a", 4),
        immutableEntry("a", 16), immutableEntry("b", 9), immutableEntry("b", 9),
        immutableEntry("c", 36)).inOrder();
  }

  @GwtIncompatible(value = "untested")
  public void testTransformValuesIsView() {
    Multimap<String, String> multimap = LinkedListMultimap.create();
    multimap.put("a", "a");
    Multimap<String, Integer> transformed =
        Multimaps.transformValues(multimap, new Function<String, Integer>() {

          @Override public Integer apply(String str) {
            return str.length();
          }
        });
    Entry<String, String> entry = multimap.entries().iterator().next();
    entry.setValue("bbb");
    assertThat(transformed.entries()).containsExactly(immutableEntry("a", 3));
  }

  @GwtIncompatible(value = "untested")
  public void testTransformListValues() {
    ListMultimap<String, Integer> multimap =
        ImmutableListMultimap.of("a", 2, "b", -3, "b", 3, "a", 4, "c", 6);
    Function<Integer, Integer> square = new Function() {
      @Override
      public Integer apply(Integer in) {
        return in * in;
      }
    };
    ListMultimap<String, Integer> transformed =
        Multimaps.transformValues(multimap, square);
    assertThat(transformed.entries()).containsExactly(immutableEntry("a", 4),
        immutableEntry("a", 16), immutableEntry("b", 9), immutableEntry("b", 9),
        immutableEntry("c", 36)).inOrder();
  }

  @GwtIncompatible(value = "untested")
  public void testTransformEntries() {
    SetMultimap<String, Integer> multimap =
        ImmutableSetMultimap.of("a", 1, "a", 4, "b", -6);
    EntryTransformer<String, Integer, String> transformer =
        new EntryTransformer<String, Integer, String>() {
          @Override
          public String transformEntry(String key, Integer value) {
            return (value >= 0) ? key : "no" + key;
          }
        };
    Multimap<String, String> transformed =
        Multimaps.transformEntries(multimap, transformer);
    assertThat(transformed.entries()).containsExactly(immutableEntry("a", "a"),
        immutableEntry("a", "a"), immutableEntry("b", "nob")).inOrder();
  }

  @GwtIncompatible(value = "untested")
  public void testTransformListEntries() {
    ListMultimap<String, Integer> multimap =
        ImmutableListMultimap.of("a", 1, "a", 4, "b", 6, "a", 4);
    EntryTransformer<String, Integer, String> transformer =
        new EntryTransformer<String, Integer, String>() {
          @Override
          public String transformEntry(String key, Integer value) {
            return key + value;
          }
        };
    ListMultimap<String, String> transformed =
        Multimaps.transformEntries(multimap, transformer);
    assertEquals(
        ImmutableListMultimap.of("a", "a1", "a", "a4", "a", "a4", "b", "b6"),
        transformed);
    assertEquals("{a=[a1, a4, a4], b=[b6]}", transformed.toString());
  }

  public <K, V> void testSynchronizedMultimapSampleCodeCompilation() {
    K key = null;

    Multimap<K, V> multimap = Multimaps.synchronizedMultimap(
        HashMultimap.<K, V>create());
    Collection<V> values = multimap.get(key);  // Needn't be in synchronized block
    synchronized (multimap) {  // Synchronizing on multimap, not values!
      Iterator<V> i = values.iterator(); // Must be in synchronized block
      while (i.hasNext()) {
        foo(i.next());
      }
    }
  }

  private static void foo(Object o) {}

  public void testFilteredKeysSetMultimapReplaceValues() {
    SetMultimap<String, Integer> multimap = LinkedHashMultimap.create();
    multimap.put("foo", 1);
    multimap.put("bar", 2);
    multimap.put("baz", 3);
    multimap.put("bar", 4);

    SetMultimap<String, Integer> filtered = Multimaps.filterKeys(
        multimap, Predicates.in(ImmutableSet.of("foo", "bar")));

    assertEquals(
        ImmutableSet.of(),
        filtered.replaceValues("baz", ImmutableSet.<Integer>of()));

    try {
      filtered.replaceValues("baz", ImmutableSet.of(5));
      fail("Expected IllegalArgumentException");
    } catch (IllegalArgumentException expected) {
    }
  }

  public void testFilteredKeysSetMultimapGetBadValue() {
    SetMultimap<String, Integer> multimap = LinkedHashMultimap.create();
    multimap.put("foo", 1);
    multimap.put("bar", 2);
    multimap.put("baz", 3);
    multimap.put("bar", 4);

    SetMultimap<String, Integer> filtered = Multimaps.filterKeys(
        multimap, Predicates.in(ImmutableSet.of("foo", "bar")));
    Set<Integer> bazSet = filtered.get("baz");
    assertThat(bazSet).isEmpty();
    try {
      bazSet.add(5);
      fail("Expected IllegalArgumentException");
    } catch (IllegalArgumentException expected) {
    }
    try {
      bazSet.addAll(ImmutableSet.of(6, 7));
      fail("Expected IllegalArgumentException");
    } catch (IllegalArgumentException expected) {
    }
  }

  public void testFilteredKeysListMultimapGetBadValue() {
    ListMultimap<String, Integer> multimap = ArrayListMultimap.create();
    multimap.put("foo", 1);
    multimap.put("bar", 2);
    multimap.put("baz", 3);
    multimap.put("bar", 4);

    ListMultimap<String, Integer> filtered = Multimaps.filterKeys(
        multimap, Predicates.in(ImmutableSet.of("foo", "bar")));
    List<Integer> bazList = filtered.get("baz");
    assertThat(bazList).isEmpty();
    try {
      bazList.add(5);
      fail("Expected IllegalArgumentException");
    } catch (IllegalArgumentException expected) {
    }
    try {
      bazList.add(0, 6);
      fail("Expected IllegalArgumentException");
    } catch (IllegalArgumentException expected) {
    }
    try {
      bazList.addAll(ImmutableList.of(7, 8));
      fail("Expected IllegalArgumentException");
    } catch (IllegalArgumentException expected) {
    }
    try {
      bazList.addAll(0, ImmutableList.of(9, 10));
      fail("Expected IllegalArgumentException");
    } catch (IllegalArgumentException expected) {
    }
  }

  @GwtIncompatible // NullPointerTester
  public void testNullPointers() {
    new NullPointerTester().testAllPublicStaticMethods(Multimaps.class);
  }
}

Other Java examples (source code examples)

Here is a short list of links related to this Java MultimapsTest.java source code file:

... this post is sponsored by my books ...

#1 New Release!

FP Best Seller

 

new blog posts

 

Copyright 1998-2021 Alvin Alexander, alvinalexander.com
All Rights Reserved.

A percentage of advertising revenue from
pages under the /java/jwarehouse URI on this website is
paid back to open source projects.