我不明白散列表是如何进行常量时间查找的,如果存在恒定数量的存储桶。假设我们有100个桶和1,000,000个元素。这显然是O(n)查找,这是复杂性的一点,要理解事物对于非常大的n值的行为。因此,散列表永远不会是常量查找,它始终是O(n)查找。
为什么人们说它平均是O(1)查找,而最坏情况下只有O(n)?
答案 0 :(得分:2)
用外行的方式挥挥手:
在一个极端,您可以拥有一个完美分布的哈希映射,每个桶只有一个值。在这种情况下,您的查找会直接返回值,并且cost是1次操作 - 或者如果您愿意,则大约为1:CustomPanel
。
在现实世界中,实现通常会通过扩展表的大小等来安排,以满足数据的要求。当你有多个项目而不是存储桶时,你开始增加复杂性。
在最坏的情况下,您在一个存储桶中有一个存储桶和n个项目。在这种情况下,它基本上就像线性搜索列表一样。因此,如果值恰好是最后一个值,则需要进行n次比较,才能找到它。或者,按照n:$ cat tst.awk
NR==FNR {
rec = (NR>1 ? rec ORS : "") $0
next
}
FNR>1 {
print prev
if ( sub(/[^[:space:]].*/,"",prev) ) {
indent = prev
}
}
{ prev=$0 }
END {
gsub(ORS,ORS indent,rec)
print indent rec ORS prev
}
$ awk -f tst.awk inputfile.txt filetowriteto.txt
Stuff {
foo {
"foostuff"
}
bar {
"barstuff"
}
input {
"inputstuff"
}
}
的顺序。
对于给定的数据集,后一种情况几乎总是/可能/。这就是为什么已经有如此多的研究和努力来提出良好的散列算法。因此,理论上可以设计一个会导致碰撞的数据集。因此,有一些方法可以最终获得O(1)
性能,除非实现调整其他方面;表大小,哈希实现等等。
答案 1 :(得分:2)
使用散列的目的是能够直接索引到表中,就像数组一样。在理想情况下,每个桶只有一个项目,我们很容易实现O(1)。
实用的哈希表将拥有比其元素更多的桶,因此每个桶只有一个元素的几率很高。如果插入表中的元素数量太大,表格将调整大小以增加存储桶数量。
每个元素都有可能具有相同的哈希值,或者所有活动哈希值都将分配给同一个桶;在那种情况下,查找时间确实是O(n)。但是,一个好的哈希表实现将被设计为最小化发生的可能性。
答案 2 :(得分:1)
说
假设我们有100个桶和1,000,000个元素。
你基本上剥夺哈希映射的真实权力,并且根本不考虑hashmap的初始容量。在每个条目都有自己的存储桶的情况下,Hashmap更有效。通过更高的hashmap容量可以实现较小的冲突百分比。每次碰撞意味着您需要遍历相应的列表。
答案 3 :(得分:0)
对于哈希表impelmentation,应考虑以下几点。
设计散列表,使其在条目数大于某个阈值的桶数时自行调整大小。如果我们希望实现自己的自定义哈希表,我们应该如何设计。
良好的哈希函数可确保条目在哈希表的桶中得到很好的分布。这使列表在一个桶中保持简短。
以上注意访问时间保持不变。