Multimap
是一个可以将一个键映射到多个值的数据结构。传统的 Java
Map<K, V>
只允许每个键对应一个值,而Multimap
允许一个键关联多个值,简化了多个值的管理。
Multimap
适用场景
Multimap 适用于需要处理一对多关系的数据结构,例如:
- 用户可以有多个角色;
- 书籍可以有多个标签;
- 一对多的业务规则映射
Multimap
使用
Multimap
出现在 Google
的 Guava
库中,它为 Java
提供了更加灵活的集合操作。Multimap
有多种实现,比如基于 List
、Set
或 Queue
。
1. 添加依赖
通过 Maven
引入Guava
依赖:
<dependency>
<groupId>com.google.guava</groupId>
<artifactId>guava</artifactId>
<version>33.2.1-jre</version>
</dependency>
2. Multimap
使用示例
import com.google.common.collect.ArrayListMultimap;
import com.google.common.collect.Multimap;
public class MultimapExample {
public static void main(String[] args) {
// 创建一个ArrayListMultimap实例
Multimap<String, String> multimap = ArrayListMultimap.create();
// 添加键值对
multimap.put("fruit", "apple");
multimap.put("fruit", "banana");
multimap.put("fruit", "orange");
multimap.put("color", "red");
multimap.put("color", "blue");
// 获取某个键的所有值
System.out.println("Fruits: " + multimap.get("fruit")); // 输出: [apple, banana, orange]
System.out.println("Colors: " + multimap.get("color")); // 输出: [red, blue]
// 遍历 Multimap
for (String key : multimap.keySet()) {
System.out.println(key + ": " + multimap.get(key));
}
// 移除某个键的某个值
multimap.remove("fruit", "banana");
System.out.println("After removing banana from fruit: " + multimap.get("fruit")); // 输出: [apple, orange]
// 删除键及其所有关联的值
multimap.removeAll("color");
System.out.println("After removing all colors: " + multimap.get("color")); // 输出: []
}
}
3. Multimap
的常见操作
put(K key, V value)
:添加键值对。get(K key)
:获取某个键对应的所有值,返回的是集合(Collection<V>
)。remove(K key, V value)
:移除某个键的某个值。removeAll(K key)
:删除键及其所有关联的值。keySet()
:获取所有键。
常见的 Multimap
实现
ArrayListMultimap
:键的值是一个ArrayList
,允许重复的值。HashMultimap
:键的值是一个HashSet
,不允许重复的值。LinkedListMultimap
:键的值是一个LinkedList
,支持插入顺序。TreeMultimap
:键的值是一个TreeSet
,按自然顺序排序,且不允许重复。
1. ArrayListMultimap
- 线程安全性: 不是线程安全的。
- 描述: 使用
ArrayList
来存储多个值,允许键关联重复的值。 - 创建方式:
Multimap<String, String> multimap = ArrayListMultimap.create();
2. HashMultimap
- 线程安全性: 不是线程安全的。
- 描述: 使用
HashSet
来存储多个值,允许键关联重复的值。 - 创建方式:
Multimap<String, String> multimap = HashMultimap.create();
3. LinkedListMultimap
- 线程安全性: 不是线程安全的。
- 描述: 使用
LinkedList
来存储多个值,允许键关联重复的值。 - 创建方式:
Multimap<String, String> multimap = LinkedListMultimap.create();
4. TreeMultimap
- 线程安全性: 不是线程安全的。
- 描述: 使用
TreeSet
来存储多个值,允许键关联重复的值。 - 创建方式:
Multimap<String, String> multimap = TreeMultimap.create();
5. ConcurrentHashMultimap
- 线程安全性: 线程安全。
- 描述: 使用 ConcurrentHashMap 和 ConcurrentHashSet 实现的线程安全 Multimap,适合高并发场景。
- 创建方式:
Multimap<String, String> multimap = Multimaps.newMultimap(
new ConcurrentHashMap<>(),
ConcurrentHashMap::newKeySet
);