文档

Java™ 教程-Java Tutorials 中文版
Map 实现
Trail: Collections
Lesson: Implementations

Map 实现

Map 实现分为通用,专用和并发实现。

通用 Map 实现

三个通用 Map 实现是 HashMapTreeMapLinkedHashMap。如果需要 SortedMap 操作或以键排序的 Collection-视图迭代,请使用 TreeMap;如果你想要最大速度而不关心迭代顺序,请使用 HashMap;如果你想要近似 HashMap 性能和插入顺序迭代,请使用 LinkedHashMap。在这方面,Map 的情况类似于 Set。同样,Set Implementations 部分中的所有其他内容也适用于 Map 实现。

LinkedHashMap 提供了 LinkedHashSet 不具备的两项功能。创建 LinkedHashMap 时,可以基于 key 的访问而不是插入顺序来对其进行排序。换句话说,仅查找与键相关联的值会将该键带到 map 的末尾。此外,LinkedHashMap 提供了 removeEldestEntry 方法,可以重写该方法,以便在将新映射添加到 map 时自动移除过时映射的策略。这使得实现自定义缓存变得非常容易。

例如,此覆盖将允许 map 多达 100 个条目,然后每次添加新条目时它将删除最旧条目,从而保持 100 个条目的稳定状态。

private static final int MAX_ENTRIES = 100;

protected boolean removeEldestEntry(Map.Entry eldest) {
    return size() > MAX_ENTRIES;
}

专用 Map 实现

有三个专用 Map 实现 — EnumMapWeakHashMapIdentityHashMapEnumMap,内部实现为 array,是一个与枚举键一起使用的高性能 Map 实现。此实现将 Map 接口的丰富性和安全性与接近数组的速度相结合。如果要将枚举映射到值,则应始终使用 EnumMap 而不是数组。

WeakHashMapMap 接口的一个实现,它只存储对其键的弱引用。仅存储弱引用允许在其键不再在 WeakHashMap 之外引用时对其进行垃圾回收。此类提供了利用弱引用功能的最简单方法。它对于实现“类似注册表”的数据结构很有用,其中当任何线程不再可以访问其键时,条目的实用程序就会消失。

IdentityHashMap 是基于哈希表的基于身份的 Map 实现。此类对于拓扑保留对象图转换非常有用,例如序列化或深度复制。要执行此类转换,你需要维护一个基于身份的“节点表”,以跟踪已经看到的对象。基于身份的 map 还用于维护动态调试器和类似系统中的对象到元信息映射。最后,基于身份的地图有助于阻止故意不正常的 equals 方法导致的“欺骗攻击”,因为 IdentityHashMap 永远不会调用键的 equals 的方法。这种实现的另一个好处是它很快。

并发 Map 实现

java.util.concurrent 包中包含 ConcurrentMap 接口,该接口继承了 Map 原子的 putIfAbsentremovereplace 方法,且 ConcurrentHashMap 实现那个接口。

ConcurrentHashMap 是一个由哈希表支持的高度并发、高性能的实现。执行获取时,此实现永远不会阻塞,并允许客户端选择更新的并发级别。它旨在作为 Hashtable 的替代品:除了实现 ConcurrentMap 之外,它还支持 Hashtable 特有的所有遗留方法。同样,如果你不需要遗留操作,请小心使用 ConcurrentMap 接口对其进行操作。


Previous page: List Implementations
Next page: Queue Implementations