一、MultiSet学习笔记
首先,我们来假定一个场景,统计一个词在文档中出现了多少次,传统的做法是这样的:。
我们可以这样来实现,
1 | Map<String, Integer> counts = new HashMap<String, Integer>(); |
1.1.什么是MultiSet
Guava提供了一个新集合类型 Multiset,它可以多次添加相等的元素,我们可以这样来看待MultiSet
没有元素顺序限制的ArrayList<E>,也就是说Multiset {a, a, b}和{a, b, a}是相等的。Map<E, Integer>,键为元素,值为计数。
没有元素顺序限制的ArrayList<E>
当把Multiset看成普通的Collection时,它表现得就像无序的ArrayList
- add(E)添加单个给定元素
- iterator()返回一个迭代器,包含Multiset的所有元素(包括重复的元素)
- size()返回所有元素的总个数(包括重复的元素)
1 | public void testHashMultiset(){ |
当把Multiset看作Map<E, Integer>时,它也提供了符合性能期望的查询操作:
count(Object)返回给定元素的计数。HashMultiset.count的复杂度为O(1),TreeMultiset.count的复杂度为O(log n)。entrySet()返回Set<Multiset.Entry<E>>,和Map的entrySet类似。elementSet()返回所有不重复元素的Set<E>,和Map的keySet()类似。- 所有
Multiset实现的内存消耗随着不重复元素的个数线性增长。
1 | public void testHashMultiset(){ |
注意,Multiset.addAll(Collection)可以添加Collection中的所有元素并进行计数,这比用for循环往Map添加元素和计数方便多了。
Multiset常用方法
| 方法 | 描述 |
|---|---|
| count(E) | 给定元素在Multiset中的计数 |
| elementSet() | Multiset中不重复元素的集合,类型为Set<E> |
| entrySet() | 和Map的entrySet类似,返回Set<Multiset.Entry<E>>,其中包含的Entry支持getElement()和getCount()方法 |
| add(E, int) | 增加给定元素在Multiset中的计数 |
| remove(E, int) | 减少给定元素在Multiset中的计数 |
| setCount(E, int) | 设置给定元素在Multiset中的计数,不可以为负数 |
| size() | 返回集合元素的总个数(包括重复的元素) |
1.2.Multiset的各种实现
| Map | 对应的Multiset | 是否支持null元素 |
|---|---|---|
| HashMap | HashMultiset | 是 |
| TreeMap | TreeMultiset | 是 |
| LinkedHashMap | LinkedHashMultiset | 是 |
| ConcurrentHashMap | ConcurrentHashMultiset | 否 |
| ImmutableMap | ImmutableMultiset | 否 |