不同初始容量和负载因子的哈希图性能

2022-09-02 01:39:19

这是我的情况。我正在使用两个java.util.HashMap在Tomcat上运行的Java Web应用程序中存储一些常用的数据。我知道每个哈希映射的确切条目数量。键将分别是字符串和整数。

我的问题是,设置初始容量和负载因子的最佳方法是什么?

我是否应将容量设置为等于它将具有的元素数和负载容量设置为 1.0?我希望在不使用太多内存的情况下获得绝对最佳性能。然而,我担心,这张桌子不会以最佳方式填满。使用所需确切大小的表格,是否会发生键冲突,导致(通常很短)扫描以找到正确的元素?

假设(这是一个延伸)哈希函数是整数键的简单mod 5,这是否意味着键5,10,15将命中相同的桶,然后导致搜索填充它们旁边的桶?较大的初始容量是否会提高性能?

此外,如果有比哈希图更好的数据结构,我也对此持完全开放态度。


答案 1

在没有完美的数据哈希函数的情况下,假设这真的不是对真正无关紧要的东西的微优化,我会尝试以下方法:

假设在大多数情况下,HashMap 使用的默认负载容量 (.75) 是一个不错的值。在这种情况下,您可以使用它,并根据您自己对它将容纳的项目数量的了解来设置HashMap的初始容量 - 将其设置为初始容量x .75 =项目数(四舍五入)。

如果它是一个更大的地图,在高速查找非常关键的情况下,我建议使用某种trie而不是哈希地图。对于长字符串,在大型映射中,通过使用更面向字符串的数据结构(如 trie),可以节省空间和一些时间。


答案 2

假设您的哈希函数是“好的”,最好的办法是将初始大小设置为预期的元素数,假设您可以便宜地获得良好的估计值。这样做是个好主意,因为当HashMap调整大小时,它必须重新计算表中每个键的哈希值。

将负载系数保留为 。根据经验选择 的值,作为哈希查找性能和主哈希数组的空间使用之间的良好折衷。当您将负载因子推高时,平均查找时间将显著增加。0.750.75

如果你想深入研究哈希表行为的数学:Donald Knuth(1998)。计算机编程的艺术'。3:排序和搜索(第2版)。艾迪生-卫斯理。第513-558页。国际标准书号0-201-89685-0。