1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package com.google.common.collect;
18
19 import static com.google.common.truth.Truth.assertThat;
20
21 import com.google.common.annotations.GwtCompatible;
22 import com.google.common.base.Joiner;
23 import com.google.common.collect.ImmutableBiMap.Builder;
24 import com.google.common.collect.testing.MapInterfaceTest;
25
26 import junit.framework.TestCase;
27
28 import java.util.Collections;
29 import java.util.LinkedHashMap;
30 import java.util.Map;
31 import java.util.Map.Entry;
32 import java.util.Set;
33
34
35
36
37
38
39 @GwtCompatible(emulated = true)
40 public class ImmutableBiMapTest extends TestCase {
41
42
43
44 public static abstract class AbstractMapTests<K, V>
45 extends MapInterfaceTest<K, V> {
46 public AbstractMapTests() {
47 super(false, false, false, false, false);
48 }
49
50 @Override protected Map<K, V> makeEmptyMap() {
51 throw new UnsupportedOperationException();
52 }
53
54 private static final Joiner joiner = Joiner.on(", ");
55
56 @Override protected void assertMoreInvariants(Map<K, V> map) {
57
58 BiMap<K, V> bimap = (BiMap<K, V>) map;
59
60 for (Entry<K, V> entry : map.entrySet()) {
61 assertEquals(entry.getKey() + "=" + entry.getValue(),
62 entry.toString());
63 assertEquals(entry.getKey(), bimap.inverse().get(entry.getValue()));
64 }
65
66 assertEquals("{" + joiner.join(map.entrySet()) + "}",
67 map.toString());
68 assertEquals("[" + joiner.join(map.entrySet()) + "]",
69 map.entrySet().toString());
70 assertEquals("[" + joiner.join(map.keySet()) + "]",
71 map.keySet().toString());
72 assertEquals("[" + joiner.join(map.values()) + "]",
73 map.values().toString());
74
75 assertEquals(Sets.newHashSet(map.entrySet()), map.entrySet());
76 assertEquals(Sets.newHashSet(map.keySet()), map.keySet());
77 }
78 }
79
80 public static class MapTests extends AbstractMapTests<String, Integer> {
81 @Override protected Map<String, Integer> makeEmptyMap() {
82 return ImmutableBiMap.of();
83 }
84
85 @Override protected Map<String, Integer> makePopulatedMap() {
86 return ImmutableBiMap.of("one", 1, "two", 2, "three", 3);
87 }
88
89 @Override protected String getKeyNotInPopulatedMap() {
90 return "minus one";
91 }
92
93 @Override protected Integer getValueNotInPopulatedMap() {
94 return -1;
95 }
96 }
97
98 public static class InverseMapTests
99 extends AbstractMapTests<String, Integer> {
100 @Override protected Map<String, Integer> makeEmptyMap() {
101 return ImmutableBiMap.of();
102 }
103
104 @Override protected Map<String, Integer> makePopulatedMap() {
105 return ImmutableBiMap.of(1, "one", 2, "two", 3, "three").inverse();
106 }
107
108 @Override protected String getKeyNotInPopulatedMap() {
109 return "minus one";
110 }
111
112 @Override protected Integer getValueNotInPopulatedMap() {
113 return -1;
114 }
115 }
116
117 public static class CreationTests extends TestCase {
118 public void testEmptyBuilder() {
119 ImmutableBiMap<String, Integer> map
120 = new Builder<String, Integer>().build();
121 assertEquals(Collections.<String, Integer>emptyMap(), map);
122 assertEquals(Collections.<Integer, String>emptyMap(), map.inverse());
123 assertSame(ImmutableBiMap.of(), map);
124 }
125
126 public void testSingletonBuilder() {
127 ImmutableBiMap<String, Integer> map = new Builder<String, Integer>()
128 .put("one", 1)
129 .build();
130 assertMapEquals(map, "one", 1);
131 assertMapEquals(map.inverse(), 1, "one");
132 }
133
134 public void testBuilder() {
135 ImmutableBiMap<String, Integer> map
136 = ImmutableBiMap.<String, Integer>builder()
137 .put("one", 1)
138 .put("two", 2)
139 .put("three", 3)
140 .put("four", 4)
141 .put("five", 5)
142 .build();
143 assertMapEquals(map,
144 "one", 1, "two", 2, "three", 3, "four", 4, "five", 5);
145 assertMapEquals(map.inverse(),
146 1, "one", 2, "two", 3, "three", 4, "four", 5, "five");
147 }
148
149 public void testBuilderPutAllWithEmptyMap() {
150 ImmutableBiMap<String, Integer> map = new Builder<String, Integer>()
151 .putAll(Collections.<String, Integer>emptyMap())
152 .build();
153 assertEquals(Collections.<String, Integer>emptyMap(), map);
154 }
155
156 public void testBuilderPutAll() {
157 Map<String, Integer> toPut = new LinkedHashMap<String, Integer>();
158 toPut.put("one", 1);
159 toPut.put("two", 2);
160 toPut.put("three", 3);
161 Map<String, Integer> moreToPut = new LinkedHashMap<String, Integer>();
162 moreToPut.put("four", 4);
163 moreToPut.put("five", 5);
164
165 ImmutableBiMap<String, Integer> map = new Builder<String, Integer>()
166 .putAll(toPut)
167 .putAll(moreToPut)
168 .build();
169 assertMapEquals(map,
170 "one", 1, "two", 2, "three", 3, "four", 4, "five", 5);
171 assertMapEquals(map.inverse(),
172 1, "one", 2, "two", 3, "three", 4, "four", 5, "five");
173 }
174
175 public void testBuilderReuse() {
176 Builder<String, Integer> builder = new Builder<String, Integer>();
177 ImmutableBiMap<String, Integer> mapOne = builder
178 .put("one", 1)
179 .put("two", 2)
180 .build();
181 ImmutableBiMap<String, Integer> mapTwo = builder
182 .put("three", 3)
183 .put("four", 4)
184 .build();
185
186 assertMapEquals(mapOne, "one", 1, "two", 2);
187 assertMapEquals(mapOne.inverse(), 1, "one", 2, "two");
188 assertMapEquals(mapTwo, "one", 1, "two", 2, "three", 3, "four", 4);
189 assertMapEquals(mapTwo.inverse(),
190 1, "one", 2, "two", 3, "three", 4, "four");
191 }
192
193 public void testBuilderPutNullKey() {
194 Builder<String, Integer> builder = new Builder<String, Integer>();
195 try {
196 builder.put(null, 1);
197 fail();
198 } catch (NullPointerException expected) {
199 }
200 }
201
202 public void testBuilderPutNullValue() {
203 Builder<String, Integer> builder = new Builder<String, Integer>();
204 try {
205 builder.put("one", null);
206 fail();
207 } catch (NullPointerException expected) {
208 }
209 }
210
211 public void testBuilderPutNullKeyViaPutAll() {
212 Builder<String, Integer> builder = new Builder<String, Integer>();
213 try {
214 builder.putAll(Collections.<String, Integer>singletonMap(null, 1));
215 fail();
216 } catch (NullPointerException expected) {
217 }
218 }
219
220 public void testBuilderPutNullValueViaPutAll() {
221 Builder<String, Integer> builder = new Builder<String, Integer>();
222 try {
223 builder.putAll(Collections.<String, Integer>singletonMap("one", null));
224 fail();
225 } catch (NullPointerException expected) {
226 }
227 }
228
229 public void testPuttingTheSameKeyTwiceThrowsOnBuild() {
230 Builder<String, Integer> builder = new Builder<String, Integer>()
231 .put("one", 1)
232 .put("one", 1);
233
234 try {
235 builder.build();
236 fail();
237 } catch (IllegalArgumentException expected) {
238 assertTrue(expected.getMessage().contains("one"));
239 }
240 }
241
242 public void testOf() {
243 assertMapEquals(
244 ImmutableBiMap.of("one", 1),
245 "one", 1);
246 assertMapEquals(
247 ImmutableBiMap.of("one", 1).inverse(),
248 1, "one");
249 assertMapEquals(
250 ImmutableBiMap.of("one", 1, "two", 2),
251 "one", 1, "two", 2);
252 assertMapEquals(
253 ImmutableBiMap.of("one", 1, "two", 2).inverse(),
254 1, "one", 2, "two");
255 assertMapEquals(
256 ImmutableBiMap.of("one", 1, "two", 2, "three", 3),
257 "one", 1, "two", 2, "three", 3);
258 assertMapEquals(
259 ImmutableBiMap.of("one", 1, "two", 2, "three", 3).inverse(),
260 1, "one", 2, "two", 3, "three");
261 assertMapEquals(
262 ImmutableBiMap.of("one", 1, "two", 2, "three", 3, "four", 4),
263 "one", 1, "two", 2, "three", 3, "four", 4);
264 assertMapEquals(
265 ImmutableBiMap.of(
266 "one", 1, "two", 2, "three", 3, "four", 4).inverse(),
267 1, "one", 2, "two", 3, "three", 4, "four");
268 assertMapEquals(
269 ImmutableBiMap.of(
270 "one", 1, "two", 2, "three", 3, "four", 4, "five", 5),
271 "one", 1, "two", 2, "three", 3, "four", 4, "five", 5);
272 assertMapEquals(
273 ImmutableBiMap.of(
274 "one", 1, "two", 2, "three", 3, "four", 4, "five", 5).inverse(),
275 1, "one", 2, "two", 3, "three", 4, "four", 5, "five");
276 }
277
278 public void testOfNullKey() {
279 try {
280 ImmutableBiMap.of(null, 1);
281 fail();
282 } catch (NullPointerException expected) {
283 }
284
285 try {
286 ImmutableBiMap.of("one", 1, null, 2);
287 fail();
288 } catch (NullPointerException expected) {
289 }
290 }
291
292 public void testOfNullValue() {
293 try {
294 ImmutableBiMap.of("one", null);
295 fail();
296 } catch (NullPointerException expected) {
297 }
298
299 try {
300 ImmutableBiMap.of("one", 1, "two", null);
301 fail();
302 } catch (NullPointerException expected) {
303 }
304 }
305
306 public void testOfWithDuplicateKey() {
307 try {
308 ImmutableBiMap.of("one", 1, "one", 1);
309 fail();
310 } catch (IllegalArgumentException expected) {
311 assertTrue(expected.getMessage().contains("one"));
312 }
313 }
314
315 public void testCopyOfEmptyMap() {
316 ImmutableBiMap<String, Integer> copy
317 = ImmutableBiMap.copyOf(Collections.<String, Integer>emptyMap());
318 assertEquals(Collections.<String, Integer>emptyMap(), copy);
319 assertSame(copy, ImmutableBiMap.copyOf(copy));
320 assertSame(ImmutableBiMap.of(), copy);
321 }
322
323 public void testCopyOfSingletonMap() {
324 ImmutableBiMap<String, Integer> copy
325 = ImmutableBiMap.copyOf(Collections.singletonMap("one", 1));
326 assertMapEquals(copy, "one", 1);
327 assertSame(copy, ImmutableBiMap.copyOf(copy));
328 }
329
330 public void testCopyOf() {
331 Map<String, Integer> original = new LinkedHashMap<String, Integer>();
332 original.put("one", 1);
333 original.put("two", 2);
334 original.put("three", 3);
335
336 ImmutableBiMap<String, Integer> copy = ImmutableBiMap.copyOf(original);
337 assertMapEquals(copy, "one", 1, "two", 2, "three", 3);
338 assertSame(copy, ImmutableBiMap.copyOf(copy));
339 }
340
341 public void testEmpty() {
342 ImmutableBiMap<String, Integer> bimap = ImmutableBiMap.of();
343 assertEquals(Collections.<String, Integer>emptyMap(), bimap);
344 assertEquals(Collections.<String, Integer>emptyMap(), bimap.inverse());
345 }
346
347 public void testFromHashMap() {
348 Map<String, Integer> hashMap = Maps.newLinkedHashMap();
349 hashMap.put("one", 1);
350 hashMap.put("two", 2);
351 ImmutableBiMap<String, Integer> bimap = ImmutableBiMap.copyOf(
352 ImmutableMap.of("one", 1, "two", 2));
353 assertMapEquals(bimap, "one", 1, "two", 2);
354 assertMapEquals(bimap.inverse(), 1, "one", 2, "two");
355 }
356
357 public void testFromImmutableMap() {
358 ImmutableBiMap<String, Integer> bimap = ImmutableBiMap.copyOf(
359 new ImmutableMap.Builder<String, Integer>()
360 .put("one", 1)
361 .put("two", 2)
362 .put("three", 3)
363 .put("four", 4)
364 .put("five", 5)
365 .build());
366 assertMapEquals(bimap,
367 "one", 1, "two", 2, "three", 3, "four", 4, "five", 5);
368 assertMapEquals(bimap.inverse(),
369 1, "one", 2, "two", 3, "three", 4, "four", 5, "five");
370 }
371
372 public void testDuplicateValues() {
373 ImmutableMap<String, Integer> map
374 = new ImmutableMap.Builder<String, Integer>()
375 .put("one", 1)
376 .put("two", 2)
377 .put("uno", 1)
378 .put("dos", 2)
379 .build();
380
381 try {
382 ImmutableBiMap.copyOf(map);
383 fail();
384 } catch (IllegalArgumentException expected) {
385 assertTrue(expected.getMessage().contains("1"));
386 }
387 }
388 }
389
390 public static class BiMapSpecificTests extends TestCase {
391
392 @SuppressWarnings("deprecation")
393 public void testForcePut() {
394 ImmutableBiMap<String, Integer> bimap = ImmutableBiMap.copyOf(
395 ImmutableMap.of("one", 1, "two", 2));
396 try {
397 bimap.forcePut("three", 3);
398 fail();
399 } catch (UnsupportedOperationException expected) {}
400 }
401
402 public void testKeySet() {
403 ImmutableBiMap<String, Integer> bimap = ImmutableBiMap.copyOf(
404 ImmutableMap.of("one", 1, "two", 2, "three", 3, "four", 4));
405 Set<String> keys = bimap.keySet();
406 assertEquals(Sets.newHashSet("one", "two", "three", "four"), keys);
407 assertThat(keys).has().exactly("one", "two", "three", "four").inOrder();
408 }
409
410 public void testValues() {
411 ImmutableBiMap<String, Integer> bimap = ImmutableBiMap.copyOf(
412 ImmutableMap.of("one", 1, "two", 2, "three", 3, "four", 4));
413 Set<Integer> values = bimap.values();
414 assertEquals(Sets.newHashSet(1, 2, 3, 4), values);
415 assertThat(values).has().exactly(1, 2, 3, 4).inOrder();
416 }
417
418 public void testDoubleInverse() {
419 ImmutableBiMap<String, Integer> bimap = ImmutableBiMap.copyOf(
420 ImmutableMap.of("one", 1, "two", 2));
421 assertSame(bimap, bimap.inverse().inverse());
422 }
423 }
424
425 private static <K, V> void assertMapEquals(Map<K, V> map,
426 Object... alternatingKeysAndValues) {
427 int i = 0;
428 for (Entry<K, V> entry : map.entrySet()) {
429 assertEquals(alternatingKeysAndValues[i++], entry.getKey());
430 assertEquals(alternatingKeysAndValues[i++], entry.getValue());
431 }
432 }
433 }
434