我是菜鸟我只学习精简版http://blog.csdn.net/v_JULY_v/article/details/6256463
hash表算法:
就是把任意长度的输入通过散列算法,变换成固定长度的输出,该输出就是散列值。
这种转换是一种压缩映射,也就是,散列值的空间通常远小于输入的空间。
不同的输入可能会散列成相同的输出,而不可能从散列值来唯一的确定输入值。
元素特征转变为数组下标的方法就是散列法。
散列法当然不止一种,下面列出三种比较常用的
1 除法散列法
index = value % 16
2 平方散列法
index = (value * value) >> 28
3 斐波那契(Fibonacci)散列法
对于16位整数而言,这个乘数是40503
对于32位整数而言,这个乘数是2654435769
对于64位整数而言,这个乘数是11400714819323198485
hash 表的使用案例
搜索引擎会通过日志文件把用户每次检索使用的所有检索串都记录下来,每个查询串的长度为1-255字节。
假设目前有一千万个记录(这些查询串的重复度比较高,虽然总数是1千万,但如果除去重复后,不超过3百万个。一个查询串的重复度越高,说明查询它的用户越多,也就是越热门。),请你统计最热门的10个查询串,要求使用的内存不能超过1G。
1 Query统计
维护一个Key为Query字串,Value为该Query出现次数的HashTable,每次读取一个Query,如果该字串不在Table中,那么加入该字串,并且将Value值设为1;如果该字串在Table中,那么将该字串的计数加一即可。最终我们在O(N)的时间复杂度内完成了对该海量数据的处理。
2 使用堆找出 top 10
维护一个K(该题目中是10)大小的小根堆,然后遍历300万的Query,分别和根元素进行对比。
堆顶存放的是整个堆中最小的数,现在遍历N个数,把最先遍历到的k个数存放到最小堆中。
而后遍历后续的N-K个数,一一与堆顶元素进行比较,如果遍历到的Xi大于堆顶元素Xmin,则把Xi放入堆中,而后更新整个堆,如果Xi<Xmin,则不更新堆。