我正在阅读一本教科书,它正在讨论哈希列表实现。特别是关于哈希表,教科书说:
如果元素在数组位置之间均匀分布,则链接方法工作得相当好,这种情况称为统一散列。例如,如果我们有300名员工,数组大小为100,如果每个职位大约有3名员工,给予或接受员工,那么我们仍然有一个在O(1)时间内运行的搜索功能,因为没有找到合适的员工需要3到4次比较。
这假设我们有一个包含100个元素的数组(用于哈希表),每个元素都是一个链表,用作该元素的冲突列表。
所以,我的问题是:
本段指出,根据我们的哈希算法,我们可以在O(1)时间内搜索一个元素。这让我感到惊讶,因为你的数据集越大,碰撞就越多,你的碰撞列表就越大。因此,碰撞列表将随着(n =#员工)缓慢增长,但它们会增长。
我原以为这会使算法在O(n)时间内起作用。
哈希表是否根据哈希函数和预期数据集大小进行了不同的分析?大多数算法分析似乎都没有包含指定的数据集大小,因此在这种情况下,哈希表分析包含有限大小的(n),这让我感到惊讶和困惑。
答案 0 :(得分:4)
这里没有直接提到的重要细节是假设哈希表在其加载因子超过某个阈值时自行调整大小。
乍看之下你的想法是正确的,但他们假设载荷因子将被允许无限增长(因此,如果没有任何上限,碰撞列表会慢慢增长)。
如果调整哈希表的大小而不是将加载因子保持在常数L下,则根据定义,在搜索collission列表时最多将有L个操作。由于L与N无关(表中的项目数),搜索仍然是恒定时间。
答案 1 :(得分:3)
在典型的实现中,在哈希表上的加载超过某个边界(当前Java实现使用0.75)之后,该表将动态调整自身大小。
这确保了“足够”的键可以获得O(1)平均性能。
答案 2 :(得分:-1)
工作单元是一个元素。在M个插槽中的N个项目的哈希表中查找一个元素是一个O(1)过程。
创建哈希表当然(至少)是一个O(N)进程。查找所有元素也(至少)是一个O(N)过程。
二进制搜索或树的逻辑相同:O(some_function_of_N)是查找一个元素所需的工作量(给定大小为N的数组或树)。