HashMap 通过哈希表数据结构的形式来存储键值对,这种设计的好处就是查询键值对的效率高。
我们在使用 HashMap 时,可以结合自己的场景来设置初始容量和加载因子两个参数。当查询操作较为频繁时,我们可以适当地减少加载因子;如果对内存利用率要求比较高,我可以适当的增加加载因子。
我们还可以在预知存储数据量的情况下,提前设置初始容量(初始容量 = 预知数据量 / 加载因子)。这样做的好处是可以减少 resize() 操作,提高 HashMap 的效率。
HashMap 还使用了数组 + 链表这两种数据结构相结合的方式实现了链地址法,当有哈希值冲突时,就可以将冲突的键值对链成一个链表。
但这种方式又存在一个性能问题,如果链表过长,查询数据的时间复杂度就会增加。HashMap 就在 Java8 中使用了红黑树来解决链表过长导致的查询性能下降问题。
实际应用中,我们设置初始容量,一般是 2 的整数次幂,主要是为了减少哈希冲突,均匀分布元素。