哈希表何时比搜索树更好用?

时间:2010-12-17 23:04:52

标签: c++

哈希表何时比搜索树更好用?

4 个答案:

答案 0 :(得分:9)

取决于您想要对数据结构做什么。

Operation         Hash table  Search Tree
Search            O(1)        O(log(N))
Insert            O(1)        O(log(N))
Delete            O(1)        O(log(N))
Traversal         O(N)        O(N)
Min/Max-Key       -hard-      O(log(N))
Find-Next-Key     -hard-      O(1)
  • 在Hashtable上插入,搜索取决于哈希的加载因子 桌子及其设计。设计糟糕的hastables可以进行O(N)搜索和插入。您的搜索树也是如此。

  • 根据您的碰撞,在哈希表中删除可能很麻烦 解决方案状态。

  • 遍历容器,查找最小/最大,查找下一个/上一个排序 由于排序,搜索树上的操作更好。

  • 上述搜索树的所有估算均针对“平衡”搜索树。

答案 1 :(得分:1)

当平均访问和插入时间比最佳访问和插入时间更重要时。实际上我认为搜索树通常和哈希表一样好,因为即使理论上一个比一个log的大θ更好,log n也非常快,当你开始处理n的大值时对实际差异的影响缩小了。而且,一个人的大says并没有说明常数的价值。当然,这也适用于树的复杂性,但是实现中树的常数因子通常是非常低的数,而不是哈希表。

同样,我知道理论家会在这里不同意我,但这是我们在这里处理的计算机,并且对于计算机来说,对于计算机来说,任何重要的负担都必须是不切实际的大。如果n是万亿,那么n的对数是40,而今天的计算机可以相当快地执行40次迭代。对于n的日志增长到50,你已经有超过千万亿元素。

目前的C ++标准并没有在其容器中提供哈希表,而且我认为人们对它的好处已经十多年了。

答案 2 :(得分:1)

我对事物的看法:

Operation                  Hash table(1)  SBB Search Tree(2)
.find(obj) -> obj          O(1)           O(1)*

.insert(obj)               O(1)           O(log(N))

.delete(obj)               O(1)           O(log(N))

.traverse / for x in...    O(N)           O(N)

.largerThan(obj) -> {objs} unsupported    O(log(N))
                                           \
                                            union right O(1) + parent O(1)

.sorted() -> [obj]         unsupported    no need
                                           \
                                            already sorted so no need
                                            to print out, .traverse() is O(N)

.findMin() -> obj          unsupported**  O(log(N)), maybe O(1)
                                           \
                                            descend from root, e.g.:
                                            root.left.left.left...left -> O(log(N))
                                            might be able to cache for O(1)

.findNext(obj) -> obj      unsupported    O(log(N))
                                           \
                                            first perform x=.find(obj) which is O(1)
                                            then descend from that node, e.g.:
                                            x.right.left.left...right -> O(log(N))

(1)http://en.wikipedia.org/wiki/Hash_table

(2)http://en.wikipedia.org/wiki/Self-balancing_binary_search_tree,例如http://en.wikipedia.org/wiki/Tango_treehttp://en.wikipedia.org/wiki/Splay_tree

(*)您可以将哈希表与搜索树结合使用来获取此值。没有渐近的速度或空间惩罚。否则,它是O(log(N))

(**)除非您永远不删除,否则只需缓存最小和最大的元素,并且O(1)

这些费用可以摊销。

<强>结论:

您希望在订购时使用树。

答案 3 :(得分:0)

在许多问题中,它取决于散列函数的价格。根据我的经验,对于合理的哈希函数,哈希值通常是平衡树的两倍,但它们肯定可能更慢。