Google Guava and Multimaps
It’s not uncommon in Java to build some sort of in-memory registry that contains a map with a list of items at each position. Often, these implementations look something like this (excluding concurrency details for brevity):
private Map<String,List<Something>> stuff = new HashMap<String,List<Something>>();
// ...
public void add(String key, Something item) {
if(!stuff.containsKey(key)) {
stuff.put(key, new ArrayList<Something>());
}
stuff.get(key).add(item);
}
public List<Something> get(String key) {
return new ArrayList<Something>(stuff.get(key));
}
Google’s Guava Libraries provide a few collections to help with this common case: com.google.common.collect.Multimap
, and the more specific variants ListMultimap
, SetMultimap
, and SortedSetMultimap
.
The above code can be re-written with Guava like this:
private ListMultimap<String,Something> stuff = ArrayListMultimap.create();
// ...
public void add(String key, Something item) {
stuff.put(key, item);
}
public List<Something> get(String key) {
// might as well use the Lists convenience API while we're at it.
return Lists.newArrayList(stuff.get(key));
}
The multi-map has a variety of fancy features that can be used as well. Here are just a few examples:
// returns a composite of all values from all entries.
Collection<Something> allSomethings = stuff.values();
// A more traditional map that can be edited.
Map<String, Collection<Something>> mapView = stuff.asMap();
// remove an individual entry for a key.
boolean removed = stuff.remove(key, someVal);
// remove all for a key
List<Something> removedSomethings = stuff.remove(key);
// One for each value in the map. Updating this collection updates the map.
Collection<Map.Entry<String,Something>> allEntries = stuff.entries();
All of the collections returned by the various API are views of the multimap. This can make it particularly easy to work with the map in a variety of ways. It does mean you should probably perform defensive copying anywhere you might be exposing these APIs (generally good practice in most cases, anyway).