一个股票交易系统的后台,为了能快速查找各种股票代码的Tick,会计算其哈希值,然后存贮在哈希表里面。一个好的哈希函数应该能实现很好地分布性,减少冲突。这里选取了几种常用的字符串哈希,包括BKDRHash,APHash,JSHash,RSHash,SDBMHash,PJWHash,ELFHash和DJBHash,通过在不同的字符串集合测试,来测试其性能。
各种常用算法
BKDRHash
BKDRHash是Kernighan和Dennis在《The C programming language》中提出的。这个算法的常数131是如何选取的,尚未可知,有知情者可以留言。
public static int bkdrhash(String str) { final int seed = 131; int hash = 0; for (int i = 0; i < str.length(); i++) { hash = hash * seed + (int)str.charAt(i); } return hash & 0x7FFFFFFF; }
APHash
Arash Partow提出了这个算法,声称具有很好地分布性。
public static int aphash(String str) { int hash = 0; for (int i = 0; i < str.length(); i++) { if ((i & 1) == 0) { hash ^= (hash << 7) ^ (str.charAt(i)) ^ (hash >> 3); } else { hash ^= ~((hash << 11) ^ (str.charAt(i)) ^ (hash >> 5)); } } return hash & 0x7FFFFFFF; }
JSHash
Justin Sobel提出的基于位的函数函数。
public static int jshash(String str) { int hash = 0; for (int i = 0; i < str.length(); i++) { hash ^= (hash << 5) + (int)str.charAt(i) + (hash >> 2); } return hash & 0x7FFFFFFF; }
RSHash
其作者是Robert Sedgwicks。实现如下:
public static int rshash(String str) { int hash = 0; int a = 63689; final int b = 378551; for (int i = 0; i < str.length(); i++) { hash = hash * a + (int)str.charAt(i); a *= b; } return hash & 0x7FFFFFFF; }
SDBMHash
SDBM项目使用的哈希函数,声称对所有的数据