問題背景
1、在解決memcache的分布式存儲的時候,用戶端需要選擇存儲節點;
2、正常取模運算的hash算法:叢集中機器上下線之後,命中率急劇下降,緩存需要重建立立,瞬間會給DB帶來極高的系統負載;
3、一緻性hash算法:叢集中機器上下線之後,能保持較高的命中率。
設計核心點
1、cache遷移少(提高命中率)
2、key分布均勻(負載均衡)
算法解讀
基本思想
不僅僅key進行hash,機器節點本身也進行hash
1、取0~2^32-1的環
2、算機器的hash,劃分區間
3、存取時,算key的hash,選擇區間的機器
圖解參見連結: https://blog.csdn.net/lihao21/article/details/54193868
虛拟節點
一緻性hash解決命中率問題,虛拟節點解決key的分布均勻問題(負載均衡)
1、使用一般的hash運算,伺服器的映射地點的分布非常不均勻;
2、使用虛拟節點的思想,為每個實體節點(伺服器)在圓環上配置設定100~200個點。
3、這樣就能抑制分布不均勻,最大限度地減小伺服器增減時的緩存重新分布。
源碼解讀(采用一緻性hash時,即定義枚舉型變量Locator為CONSISTENT時)
伺服器對于hash區間的割分
KetamaNodeLocator類中
//機器劃分hash區間,記錄在本類的ketamaNodes成員屬性中
protected void setKetamaNodes(List<MemcachedNode> nodes) {
TreeMap<Long, MemcachedNode> newNodeMap =
new TreeMap<Long, MemcachedNode>();
int numReps = config.getNodeRepetitions();
int nodeCount = nodes.size();
int totalWeight = ;
if (isWeightedKetama) {
for (MemcachedNode node : nodes) {
totalWeight += weights.get(node.getSocketAddress());
}
}
for (MemcachedNode node : nodes) {
if (isWeightedKetama) {
//帶權重的一緻性hash算法節點劃分@[email protected]
int thisWeight = weights.get(node.getSocketAddress());
float percent = (float)thisWeight / (float)totalWeight;
int pointerPerServer = (int)((Math.floor((float)(percent * (float)config.getNodeRepetitions() / * (float)nodeCount + ))) * );
for (int i = ; i < pointerPerServer / ; i++) {
for(long position : ketamaNodePositionsAtIteration(node, i)) {
newNodeMap.put(position, node);
getLogger().debug("Adding node %s with weight %s in position %d", node, thisWeight, position);
}
}
} else {
// Ketama does some special work with md5 where it reuses chunks.
// Check to be backwards compatible, the hash algorithm does not
// matter for Ketama, just the placement should always be done using
// MD5
//一緻性hash算法節點劃分@[email protected]
if (hashAlg == DefaultHashAlgorithm.KETAMA_HASH) {
for (int i = ; i < numReps / ; i++) {
for(long position : ketamaNodePositionsAtIteration(node, i)) {
newNodeMap.put(position, node);
getLogger().debug("Adding node %s in position %d", node, position);
}
}
} else {
//非一緻性hash算法節點劃分@[email protected]
for (int i = ; i < numReps; i++) {
newNodeMap.put(hashAlg.hash(config.getKeyForNode(node, i)), node);
}
}
}
}
assert newNodeMap.size() == numReps * nodes.size();
ketamaNodes = newNodeMap;
}
@[email protected]:非一緻性hash算法節點劃分
1、重複numReps次,每次都是計算一個虛拟節點的hash結果
2、計算每個虛拟節點進行hash運算的key值:config.getKeyForNode(node, i)
KetamaNodeKeyFormatter類中
public String getKeyForNode(MemcachedNode node, int repetition) {
// Carrried over from the DefaultKetamaNodeLocatorConfiguration:
// Internal Using the internal map retrieve the socket addresses
// for given nodes.
// I'm aware that this code is inherently thread-unsafe as
// I'm using a HashMap implementation of the map, but the worst
// case ( I believe) is we're slightly in-efficient when
// a node has never been seen before concurrently on two different
// threads, so it the socketaddress will be requested multiple times!
// all other cases should be as fast as possible.
String nodeKey = nodeKeys.get(node);
if (nodeKey == null) {
switch(this.format) {
case LIBMEMCACHED:
InetSocketAddress address = (InetSocketAddress)node.getSocketAddress();
nodeKey = address.getHostName();
if (address.getPort() != ) {
nodeKey += ":" + address.getPort();
}
break;
case SPYMEMCACHED:
nodeKey = String.valueOf(node.getSocketAddress());
if (nodeKey.startsWith("/")) {
nodeKey = nodeKey.substring();
}
break;
default:
assert false;
}
nodeKeys.put(node, nodeKey);
}
return nodeKey + "-" + repetition;
}
計算結果就是"SocketAddress-虛拟節點重複數"(10.10.1.118:11411-0)
3、根據key計算出虛拟節點的hash結果 DefaultHashAlgorithm類中
/**
* Compute the hash for the given key.
*
* @return a positive integer hash
*/
public long hash(final String k) {
long rv = ;
int len = k.length();
switch (this) {
case NATIVE_HASH:
rv = k.hashCode();
break;
case CRC_HASH:
// return (crc32(shift) >> 16) & 0x7fff;
CRC32 crc32 = new CRC32();
crc32.update(KeyUtil.getKeyBytes(k));
rv = (crc32.getValue() >> ) & ;
break;
case FNV1_64_HASH:
// Thanks to [email protected] for the pointer
rv = FNV_64_INIT;
for (int i = ; i < len; i++) {
rv *= FNV_64_PRIME;
rv ^= k.charAt(i);
}
break;
case FNV1A_64_HASH:
rv = FNV_64_INIT;
for (int i = ; i < len; i++) {
rv ^= k.charAt(i);
rv *= FNV_64_PRIME;
}
break;
case FNV1_32_HASH:
rv = FNV_32_INIT;
for (int i = ; i < len; i++) {
rv *= FNV_32_PRIME;
rv ^= k.charAt(i);
}
break;
case FNV1A_32_HASH:
rv = FNV_32_INIT;
for (int i = ; i < len; i++) {
rv ^= k.charAt(i);
rv *= FNV_32_PRIME;
}
break;
case KETAMA_HASH:
byte[] bKey = computeMd5(k);
rv = ((long) (bKey[] & ) << )
| ((long) (bKey[] & ) << )
| ((long) (bKey[] & ) << )
| (bKey[] & );
break;
default:
assert false;
}
return rv & L; /* Truncate to 32-bits */
}
@[email protected]一緻性hash算法節點劃分
1、對于每個節點要算出numReps個虛拟節點,每組算出四個,一共算numReps/4組;
2、算一組四個虛拟節點:ketamaNodePositionsAtIteration(node, i)
KetamaNodeLocator類中
private List<Long> ketamaNodePositionsAtIteration(MemcachedNode node, int iteration) {
List<Long> positions = new ArrayList<Long>();
byte[] digest = DefaultHashAlgorithm.computeMd5(config.getKeyForNode(node, iteration));
for (int h = ; h < ; h++) {
Long k = ((long) (digest[ + h * ] & ) << )
| ((long) (digest[ + h * ] & ) << )
| ((long) (digest[ + h * ] & ) << )
| (digest[h * ] & );
positions.add(k);
}
return positions;
}
config.getKeyForNode(node, iteration)還是取出"SocketAddress-虛拟節點重複數"(10.10.1.118:11411-0)作為key值
DefaultHashAlgorithm類中computeMd5方法用key算出md5值digest位元組數組
digest位元組數組是16位的,每四位一取,倒序拼接成32位的二進制數【(long) (digest[3 + h * 4] & 0xFF) << 24是将相鄰四個位元組中的最後一位以二進制左移32位】,作為虛拟節點最終在hash結果集合内的落點,一組就算出四個虛拟節點的位置
@[email protected]帶權重的一緻性hash算法節點劃分 1、從weights中獲得每個節點的權重(如果是帶權重的節點,之前初始化的時候會設定這裡的值),算出每個節點權重所占的百分比;
2、根據百分比算出每個節點應該有的虛拟節點數(因為floor的關系,這裡算出來的虛拟節點數可能不等于重複率乘上節點數量,一般會比這個值小一點,原權重比例也會有所偏差,可以以權重2、3、5,重複率13,節點數3進行測算)
3、對于每個節點的虛拟節點,按照4個一組進行計算計算虛拟節點的hash結果ketamaNodePositionsAtIteration(node, i),和不帶權重的ketama計算方式是一樣的
用戶端對于key值的計算
KetamaNodeLocator類中
public MemcachedNode getPrimary(final String k) {
MemcachedNode rv = getNodeForKey(hashAlg.hash(k));
assert rv != null : "Found no node for key " + k;
return rv;
}
1、根據存儲對象的key計算出hash結果hashAlg.hash(k),與計算伺服器的虛拟節點hash結果用的是一個方法
2、根據算得的hash坐标在環中找到應該存儲的伺服器節點getNodeForKey(long hash)
MemcachedNode getNodeForKey(long hash) {
final MemcachedNode rv;
if (!ketamaNodes.containsKey(hash)) {
// Java 1.6 adds a ceilingKey method, but I'm still stuck in 1.5
// in a lot of places, so I'm doing this myself.
SortedMap<Long, MemcachedNode> tailMap = getKetamaNodes().tailMap(hash);
if (tailMap.isEmpty()) {
hash = getKetamaNodes().firstKey();
} else {
hash = tailMap.firstKey();
}
}
rv = getKetamaNodes().get(hash);
return rv;
}
判斷hash坐标是否正好坐落在伺服器虛拟節點上,在則直接獲得伺服器節點ip
不在,擷取hash坐标之後的弧,如果之後的弧上沒有伺服器節點ip了,說明應該繞完整個環的尾部,去找環的第一個節點,獲得伺服器節點ip
如果弧上還有伺服器節點ip的話,則選取第一個ip作為應該存儲的伺服器節點ip。
測試結果對比
不同算法結果對比
步驟:
1、将不同的算法枚舉值作為參數傳入,建立不同的memcache用戶端,建立過程根據不同的hash算法計算生成不同的伺服器hash結果集合(存儲在對應用戶端的MemcachedConnection的NodeLocator中)
2、獲得不同算法産生的NodeLocator
3、實驗标本使用線上環境某個長時間段内的大量資料進行測試,計算對應key值hash之後最終選擇的伺服器,統計對于大量資料每個算法的耗時,以及每個伺服器命中數的均勻性。
4、進行三次實驗對比
測試結果:
1st:
FNV1A_64_HASH costs:1184ms, number:2387858 perdata:0.49584188004479324ns.
10.10.1.118:11411 : 555973 , 23.28%
10.16.69.133:11411 : 533208 , 22.33%
10.16.69.135:11411 : 355425 , 14.88%
10.16.6.184:11411 : 235848 , 9.88%
10.10.1.228:11411 : 346293 , 14.50%
10.10.1.208:11411 : 361111 , 15.12%
variance:0.33143952290634493
FNV1_32_HASH costs:1174ms, number:2387858 perdata:0.49165402632819877ns.
10.10.1.118:11411 : 489055 , 20.48%
10.16.69.133:11411 : 395165 , 16.55%
10.16.69.135:11411 : 259880 , 10.88%
10.16.6.184:11411 : 232323 , 9.73%
10.10.1.228:11411 : 277434 , 11.62%
10.10.1.208:11411 : 734001 , 30.74%
variance:0.6438545073606985
KETAMA_HASH costs:2352ms, number:2387858 perdata:0.9849831941430353ns.
10.10.1.118:11411 : 411977 , 17.25%
10.16.69.133:11411 : 449525 , 18.83%
10.16.6.184:11411 : 387824 , 16.24%
10.16.69.135:11411 : 346523 , 14.51%
10.10.1.228:11411 : 382838 , 16.03%
10.10.1.208:11411 : 409171 , 17.14%
variance:0.12852730715084365
NATIVE_HASH costs:1024ms, number:2387858 perdata:0.42883622057928067ns.
10.10.1.118:11411 : 293716 , 12.30%
10.16.69.133:11411 : 209344 , 8.77%
10.16.69.135:11411 : 694618 , 29.09%
10.16.6.184:11411 : 362735 , 15.19%
10.10.1.228:11411 : 191147 , 8.00%
10.10.1.208:11411 : 636298 , 26.65%
variance:0.7987988531108471
CRC_HASH costs:1733ms, number:2387858 perdata:0.7257550490858334ns.
10.10.1.118:11411 : 347616 , 14.56%
10.16.69.133:11411 : 327404 , 13.71%
10.16.6.184:11411 : 459595 , 19.25%
10.16.69.135:11411 : 481764 , 20.18%
10.10.1.228:11411 : 395621 , 16.57%
10.10.1.208:11411 : 375858 , 15.74%
variance:0.1661475366273886
FNV1_64_HASH costs:971ms, number:2387858 perdata:0.4066405958813296ns.
10.10.1.118:11411 : 248007 , 10.39%
10.16.69.133:11411 : 324288 , 13.58%
10.16.6.184:11411 : 1051464 , 44.03%
10.16.69.135:11411 : 239652 , 10.04%
10.10.1.228:11411 : 126840 , 5.31%
10.10.1.208:11411 : 397607 , 16.65%
variance:1.7291444612562392
FNV1A_32_HASH costs:1578ms, number:2387858 perdata:0.660843316478618ns.
10.10.1.118:11411 : 312106 , 13.07%
10.16.69.133:11411 : 253577 , 10.62%
10.16.6.184:11411 : 644748 , 27.00%
10.16.69.135:11411 : 421664 , 17.66%
10.10.1.228:11411 : 323920 , 13.57%
10.10.1.208:11411 : 431843 , 18.08%
variance:0.3926374779645682
2nd:
FNV1A_64_HASH costs:1169ms, number:2387858 perdata:0.4895600994699015ns.
10.10.1.118:11411 : 555973 , 23.28%
10.16.69.133:11411 : 533208 , 22.33%
10.16.69.135:11411 : 355425 , 14.88%
10.16.6.184:11411 : 235848 , 9.88%
10.10.1.228:11411 : 346293 , 14.50%
10.10.1.208:11411 : 361111 , 15.12%
variance:0.33143952290634493
FNV1_32_HASH costs:1205ms, number:2387858 perdata:0.5046363728496418ns.
10.10.1.118:11411 : 489055 , 20.48%
10.16.69.133:11411 : 395165 , 16.55%
10.16.69.135:11411 : 259880 , 10.88%
10.16.6.184:11411 : 232323 , 9.73%
10.10.1.228:11411 : 277434 , 11.62%
10.10.1.208:11411 : 734001 , 30.74%
variance:0.6438545073606985
KETAMA_HASH costs:2314ms, number:2387858 perdata:0.9690693500199761ns.
10.10.1.118:11411 : 411977 , 17.25%
10.16.69.133:11411 : 449525 , 18.83%
10.16.6.184:11411 : 387824 , 16.24%
10.16.69.135:11411 : 346523 , 14.51%
10.10.1.228:11411 : 382838 , 16.03%
10.10.1.208:11411 : 409171 , 17.14%
variance:0.12852730715084365
NATIVE_HASH costs:987ms, number:2387858 perdata:0.4133411618278809ns.
10.10.1.118:11411 : 293716 , 12.30%
10.16.69.133:11411 : 209344 , 8.77%
10.16.69.135:11411 : 694618 , 29.09%
10.16.6.184:11411 : 362735 , 15.19%
10.10.1.228:11411 : 191147 , 8.00%
10.10.1.208:11411 : 636298 , 26.65%
variance:0.7987988531108471
CRC_HASH costs:1718ms, number:2387858 perdata:0.7194732685109416ns.
10.10.1.118:11411 : 347616 , 14.56%
10.16.69.133:11411 : 327404 , 13.71%
10.16.6.184:11411 : 459595 , 19.25%
10.16.69.135:11411 : 481764 , 20.18%
10.10.1.228:11411 : 395621 , 16.57%
10.10.1.208:11411 : 375858 , 15.74%
variance:0.1661475366273886
FNV1_64_HASH costs:1006ms, number:2387858 perdata:0.42129808388941054ns.
10.10.1.118:11411 : 248007 , 10.39%
10.16.69.133:11411 : 324288 , 13.58%
10.16.6.184:11411 : 1051464 , 44.03%
10.16.69.135:11411 : 239652 , 10.04%
10.10.1.228:11411 : 126840 , 5.31%
10.10.1.208:11411 : 397607 , 16.65%
variance:1.7291444612562392
FNV1A_32_HASH costs:1528ms, number:2387858 perdata:0.6399040478956454ns.
10.10.1.118:11411 : 312106 , 13.07%
10.16.69.133:11411 : 253577 , 10.62%
10.16.6.184:11411 : 644748 , 27.00%
10.16.69.135:11411 : 421664 , 17.66%
10.10.1.228:11411 : 323920 , 13.57%
10.10.1.208:11411 : 431843 , 18.08%
variance:0.3926374779645682
3rd:
FNV1A_64_HASH costs:1085ms, number:2387858 perdata:0.45438212825050733ns.
10.10.1.118:11411 : 555973 , 23.28%
10.16.69.133:11411 : 533208 , 22.33%
10.16.69.135:11411 : 355425 , 14.88%
10.16.6.184:11411 : 235848 , 9.88%
10.10.1.228:11411 : 346293 , 14.50%
10.10.1.208:11411 : 361111 , 15.12%
variance:0.33143952290634493
FNV1_32_HASH costs:1199ms, number:2387858 perdata:0.502123660619685ns.
10.10.1.118:11411 : 489055 , 20.48%
10.16.69.133:11411 : 395165 , 16.55%
10.16.69.135:11411 : 259880 , 10.88%
10.16.6.184:11411 : 232323 , 9.73%
10.10.1.228:11411 : 277434 , 11.62%
10.10.1.208:11411 : 734001 , 30.74%
variance:0.6438545073606985
KETAMA_HASH costs:2551ms, number:2387858 perdata:1.0683214831032668ns.
10.10.1.118:11411 : 411977 , 17.25%
10.16.69.133:11411 : 449525 , 18.83%
10.16.6.184:11411 : 387824 , 16.24%
10.16.69.135:11411 : 346523 , 14.51%
10.10.1.228:11411 : 382838 , 16.03%
10.10.1.208:11411 : 409171 , 17.14%
variance:0.12852730715084365
NATIVE_HASH costs:1050ms, number:2387858 perdata:0.43972464024242647ns.
10.10.1.118:11411 : 293716 , 12.30%
10.16.69.133:11411 : 209344 , 8.77%
10.16.69.135:11411 : 694618 , 29.09%
10.16.6.184:11411 : 362735 , 15.19%
10.10.1.228:11411 : 191147 , 8.00%
10.10.1.208:11411 : 636298 , 26.65%
variance:0.7987988531108471
CRC_HASH costs:1806ms, number:2387858 perdata:0.7563263812169736ns.
10.10.1.118:11411 : 347616 , 14.56%
10.16.69.133:11411 : 327404 , 13.71%
10.16.6.184:11411 : 459595 , 19.25%
10.16.69.135:11411 : 481764 , 20.18%
10.10.1.228:11411 : 395621 , 16.57%
10.10.1.208:11411 : 375858 , 15.74%
variance:0.1661475366273886
FNV1_64_HASH costs:1027ms, number:2387858 perdata:0.43009257669425904ns.
10.10.1.118:11411 : 248007 , 10.39%
10.16.69.133:11411 : 324288 , 13.58%
10.16.6.184:11411 : 1051464 , 44.03%
10.16.69.135:11411 : 239652 , 10.04%
10.10.1.228:11411 : 126840 , 5.31%
10.10.1.208:11411 : 397607 , 16.65%
variance:1.7291444612562392
FNV1A_32_HASH costs:1546ms, number:2387858 perdata:0.6474421845855155ns.
10.10.1.118:11411 : 312106 , 13.07%
10.16.69.133:11411 : 253577 , 10.62%
10.16.6.184:11411 : 644748 , 27.00%
10.16.69.135:11411 : 421664 , 17.66%
10.10.1.228:11411 : 323920 , 13.57%
10.10.1.208:11411 : 431843 , 18.08%
variance:0.3926374779645682
說明:每段開頭是采用的hash算法的名稱,number表示處理的總資料量,costs表示總耗時,perdata是計算得到的對于每個資料的平均處理耗時,下面是羅列的每個伺服器對應的ip、命中數和命中占比,variance表示占比計算得到的方差(乘了100倍處理)。
實驗結論:
1、對于同一标本,三次實驗采用各算法,每個伺服器的命中占比是不變的,其中KETAMA_HASH個伺服器命中占比比較均勻,其次表現較好的是CRC_HASH,其他的算法命中占比相差比較大;
2、對于同一标本,三次實驗采用各算法,所耗時間略有波動,綜合來說,NATIVE_HASH和FNV1_64_HASH耗時較少,KETAMA_HASH耗時較多,約是前兩種算法的兩倍,其他算法居于中間。
增減用戶端個數結果對比
步驟:基本步驟和上述相同,本次設定不同的伺服器台數,分别設定伺服器台數為2,4,6台,将結果進行縱向對比
測試結果:
6台:
FNV1A_64_HASH costs:1085ms, number:2387858 perdata:0.45438212825050733ns.
10.10.1.118:11411 : 555973 , 23.28%
10.16.69.133:11411 : 533208 , 22.33%
10.16.69.135:11411 : 355425 , 14.88%
10.16.6.184:11411 : 235848 , 9.88%
10.10.1.228:11411 : 346293 , 14.50%
10.10.1.208:11411 : 361111 , 15.12%
variance:0.33143952290634493
FNV1_32_HASH costs:1199ms, number:2387858 perdata:0.502123660619685ns.
10.10.1.118:11411 : 489055 , 20.48%
10.16.69.133:11411 : 395165 , 16.55%
10.16.69.135:11411 : 259880 , 10.88%
10.16.6.184:11411 : 232323 , 9.73%
10.10.1.228:11411 : 277434 , 11.62%
10.10.1.208:11411 : 734001 , 30.74%
variance:0.6438545073606985
KETAMA_HASH costs:2551ms, number:2387858 perdata:1.0683214831032668ns.
10.10.1.118:11411 : 411977 , 17.25%
10.16.69.133:11411 : 449525 , 18.83%
10.16.6.184:11411 : 387824 , 16.24%
10.16.69.135:11411 : 346523 , 14.51%
10.10.1.228:11411 : 382838 , 16.03%
10.10.1.208:11411 : 409171 , 17.14%
variance:0.12852730715084365
NATIVE_HASH costs:1050ms, number:2387858 perdata:0.43972464024242647ns.
10.10.1.118:11411 : 293716 , 12.30%
10.16.69.133:11411 : 209344 , 8.77%
10.16.69.135:11411 : 694618 , 29.09%
10.16.6.184:11411 : 362735 , 15.19%
10.10.1.228:11411 : 191147 , 8.00%
10.10.1.208:11411 : 636298 , 26.65%
variance:0.7987988531108471
CRC_HASH costs:1806ms, number:2387858 perdata:0.7563263812169736ns.
10.10.1.118:11411 : 347616 , 14.56%
10.16.69.133:11411 : 327404 , 13.71%
10.16.6.184:11411 : 459595 , 19.25%
10.16.69.135:11411 : 481764 , 20.18%
10.10.1.228:11411 : 395621 , 16.57%
10.10.1.208:11411 : 375858 , 15.74%
variance:0.1661475366273886
FNV1_64_HASH costs:1027ms, number:2387858 perdata:0.43009257669425904ns.
10.10.1.118:11411 : 248007 , 10.39%
10.16.69.133:11411 : 324288 , 13.58%
10.16.6.184:11411 : 1051464 , 44.03%
10.16.69.135:11411 : 239652 , 10.04%
10.10.1.228:11411 : 126840 , 5.31%
10.10.1.208:11411 : 397607 , 16.65%
variance:1.7291444612562392
FNV1A_32_HASH costs:1546ms, number:2387858 perdata:0.6474421845855155ns.
10.10.1.118:11411 : 312106 , 13.07%
10.16.69.133:11411 : 253577 , 10.62%
10.16.6.184:11411 : 644748 , 27.00%
10.16.69.135:11411 : 421664 , 17.66%
10.10.1.228:11411 : 323920 , 13.57%
10.10.1.208:11411 : 431843 , 18.08%
variance:0.3926374779645682
4台:
FNV1A_64_HASH costs:1147ms, number:2387858 perdata:0.48034682129339346ns.
10.10.1.118:11411 : 936837 , 39.23%
10.16.6.184:11411 : 713990 , 29.90%
10.10.1.228:11411 : 375920 , 15.74%
10.10.1.208:11411 : 361111 , 15.12%
variance:1.274646297334262
FNV1_32_HASH costs:1074ms, number:2387858 perdata:0.44977548916225335ns.
10.10.1.118:11411 : 809789 , 33.91%
10.16.6.184:11411 : 529418 , 22.17%
10.10.1.228:11411 : 314650 , 13.18%
10.10.1.208:11411 : 734001 , 30.74%
variance:0.9003891935351122
KETAMA_HASH costs:2217ms, number:2387858 perdata:0.928447168969009ns.
10.10.1.118:11411 : 653133 , 27.35%
10.16.6.184:11411 : 621488 , 26.03%
10.10.1.228:11411 : 551835 , 23.11%
10.10.1.208:11411 : 561402 , 23.51%
variance:0.2809445444425362
NATIVE_HASH costs:947ms, number:2387858 perdata:0.39658974696150273ns.
10.10.1.118:11411 : 312854 , 13.10%
10.16.6.184:11411 : 884987 , 37.06%
10.10.1.228:11411 : 191147 , 8.00%
10.10.1.208:11411 : 998870 , 41.83%
variance:2.3979443120759343
CRC_HASH costs:1574ms, number:2387858 perdata:0.6591681749919802ns.
10.10.1.118:11411 : 411390 , 17.23%
10.16.6.184:11411 : 845242 , 35.40%
10.10.1.228:11411 : 564908 , 23.66%
10.10.1.208:11411 : 566318 , 23.72%
variance:0.679887523513382
FNV1_64_HASH costs:976ms, number:2387858 perdata:0.40873452273962685ns.
10.10.1.118:11411 : 248007 , 10.39%
10.16.6.184:11411 : 1270549 , 53.21%
10.10.1.228:11411 : 471695 , 19.75%
10.10.1.208:11411 : 397607 , 16.65%
variance:3.016301833895297
FNV1A_32_HASH costs:1326ms, number:2387858 perdata:0.5553094028204357ns.
10.10.1.118:11411 : 413146 , 17.30%
10.16.6.184:11411 : 1056172 , 44.23%
10.10.1.228:11411 : 443434 , 18.57%
10.10.1.208:11411 : 475106 , 19.90%
variance:1.4911808957900026
2台:
FNV1A_64_HASH costs:1202ms, number:2387858 perdata:0.5033800167346635ns.
10.10.1.118:11411 : 1937413 , 81.14%
10.10.1.208:11411 : 450445 , 18.86%
variance:18.694518863029643
FNV1_32_HASH costs:1126ms, number:2387858 perdata:0.471552328488545ns.
10.10.1.118:11411 : 809789 , 33.91%
10.10.1.208:11411 : 1578069 , 66.09%
variance:11.587986880910444
KETAMA_HASH costs:2202ms, number:2387858 perdata:0.9221653883941173ns.
10.10.1.118:11411 : 1334362 , 55.88%
10.10.1.208:11411 : 1053496 , 44.12%
variance:9.345876737253043
NATIVE_HASH costs:1062ms, number:2387858 perdata:0.44475006470233996ns.
10.10.1.118:11411 : 1073300 , 44.95%
10.10.1.208:11411 : 1314558 , 55.05%
variance:9.255203403228546
CRC_HASH costs:1577ms, number:2387858 perdata:0.6604245311069586ns.
10.10.1.118:11411 : 959036 , 40.16%
10.10.1.208:11411 : 1428822 , 59.84%
variance:9.96766081685872
FNV1_64_HASH costs:1057ms, number:2387858 perdata:0.4426561378440426ns.
10.10.1.118:11411 : 712144 , 29.82%
10.10.1.208:11411 : 1675714 , 70.18%
variance:13.070891761052566
FNV1A_32_HASH costs:1317ms, number:2387858 perdata:0.5515403344755007ns.
10.10.1.118:11411 : 1023129 , 42.85%
10.10.1.208:11411 : 1364729 , 57.15%
variance:9.511633224617519
實驗結論:
1、不同的伺服器台數對于命中率的均勻性是有影響的;
2、KETAMA_HASH在各數量台數伺服器的情況下表現的命中均勻性都比較好;
3、CRC_HASH和FNV1A_32_HASH在某些情況下均勻性較好,某些情況下較差,具有波動性;
4、其他hash算法在各種情況下表現得均勻性都很差。
不同用戶端ip對于均勻性的影響
步驟:基本步驟和上述相同,本次設定伺服器台數為4台,三次實驗伺服器ip不同,對比三次結果伺服器命中率均勻性的不同 實驗結果:
FNV1A_64_HASH costs:1092ms, number:2387858 perdata:0.45731362585212354ns.
10.10.1.118:11411 : 936837 , 39.23%
10.16.6.184:11411 : 713990 , 29.90%
10.10.1.228:11411 : 375920 , 15.74%
10.10.1.208:11411 : 361111 , 15.12%
variance:1.274646297334262
FNV1_32_HASH costs:1213ms, number:2387858 perdata:0.5079866558229175ns.
10.10.1.118:11411 : 809789 , 33.91%
10.16.6.184:11411 : 529418 , 22.17%
10.10.1.228:11411 : 314650 , 13.18%
10.10.1.208:11411 : 734001 , 30.74%
variance:0.9003891935351122
KETAMA_HASH costs:2372ms, number:2387858 perdata:0.9933589015762244ns.
10.10.1.118:11411 : 653133 , 27.35%
10.16.6.184:11411 : 621488 , 26.03%
10.10.1.228:11411 : 551835 , 23.11%
10.10.1.208:11411 : 561402 , 23.51%
variance:0.2809445444425362
NATIVE_HASH costs:1142ms, number:2387858 perdata:0.4782528944350962ns.
10.10.1.118:11411 : 312854 , 13.10%
10.16.6.184:11411 : 884987 , 37.06%
10.10.1.228:11411 : 191147 , 8.00%
10.10.1.208:11411 : 998870 , 41.83%
variance:2.3979443120759343
CRC_HASH costs:1722ms, number:2387858 perdata:0.7211484099975795ns.
10.10.1.118:11411 : 411390 , 17.23%
10.16.6.184:11411 : 845242 , 35.40%
10.10.1.228:11411 : 564908 , 23.66%
10.10.1.208:11411 : 566318 , 23.72%
variance:0.679887523513382
FNV1_64_HASH costs:1094ms, number:2387858 perdata:0.45815119659544246ns.
10.10.1.118:11411 : 248007 , 10.39%
10.16.6.184:11411 : 1270549 , 53.21%
10.10.1.228:11411 : 471695 , 19.75%
10.10.1.208:11411 : 397607 , 16.65%
variance:3.016301833895297
FNV1A_32_HASH costs:1443ms, number:2387858 perdata:0.6043072913045918ns.
10.10.1.118:11411 : 413146 , 17.30%
10.16.6.184:11411 : 1056172 , 44.23%
10.10.1.228:11411 : 443434 , 18.57%
10.10.1.208:11411 : 475106 , 19.90%
variance:1.4911808957900026
FNV1A_64_HASH costs:1059ms, number:2387858 perdata:0.4434937085873616ns.
10.10.1.118:11411 : 555973 , 23.28%
10.16.69.133:11411 : 995377 , 41.68%
10.16.69.135:11411 : 386063 , 16.17%
10.10.1.208:11411 : 450445 , 18.86%
variance:1.2424831477658953
FNV1_32_HASH costs:1172ms, number:2387858 perdata:0.49081645558487985ns.
10.10.1.118:11411 : 489055 , 20.48%
10.16.69.133:11411 : 752254 , 31.50%
10.16.69.135:11411 : 382095 , 16.00%
10.10.1.208:11411 : 764454 , 32.01%
variance:0.7322146248064811
KETAMA_HASH costs:2288ms, number:2387858 perdata:0.9581809303568303ns.
10.10.1.118:11411 : 672247 , 28.15%
10.16.69.133:11411 : 599286 , 25.10%
10.16.69.135:11411 : 525914 , 22.02%
10.10.1.208:11411 : 590411 , 24.73%
variance:0.29719492884167864
NATIVE_HASH costs:999ms, number:2387858 perdata:0.41836658628779433ns.
10.10.1.118:11411 : 605520 , 25.36%
10.16.69.133:11411 : 380544 , 15.94%
10.16.69.135:11411 : 694618 , 29.09%
10.10.1.208:11411 : 707176 , 29.62%
variance:0.5507515972060639
CRC_HASH costs:1719ms, number:2387858 perdata:0.719892053882601ns.
10.10.1.118:11411 : 638712 , 26.75%
10.16.69.133:11411 : 499041 , 20.90%
10.16.69.135:11411 : 707826 , 29.64%
10.10.1.208:11411 : 542279 , 22.71%
variance:0.3666839176114445
FNV1_64_HASH costs:936ms, number:2387858 perdata:0.39198310787324875ns.
10.10.1.118:11411 : 263803 , 11.05%
10.16.69.133:11411 : 427774 , 17.91%
10.16.69.135:11411 : 716761 , 30.02%
10.10.1.208:11411 : 979520 , 41.02%
variance:1.5667703845361418
FNV1A_32_HASH costs:1390ms, number:2387858 perdata:0.5821116666066407ns.
10.10.1.118:11411 : 428731 , 17.95%
10.16.69.133:11411 : 796957 , 33.38%
10.16.69.135:11411 : 618340 , 25.90%
10.10.1.208:11411 : 543830 , 22.77%
variance:0.5638433094805416
FNV1A_64_HASH costs:1030ms, number:2387858 perdata:0.4313489328092374ns.
10.16.69.133:11411 : 533208 , 22.33%
10.16.6.184:11411 : 1144370 , 47.92%
10.16.69.135:11411 : 363987 , 15.24%
10.10.1.228:11411 : 346293 , 14.50%
variance:2.0951521038180405
FNV1_32_HASH costs:1035ms, number:2387858 perdata:0.43344285966753465ns.
10.16.69.133:11411 : 395165 , 16.55%
10.16.69.135:11411 : 760587 , 31.85%
10.16.6.184:11411 : 232323 , 9.73%
10.10.1.228:11411 : 999783 , 41.87%
variance:1.8403633087057236
KETAMA_HASH costs:2251ms, number:2387858 perdata:0.9426858716054305ns.
10.16.69.133:11411 : 664844 , 27.84%
10.16.6.184:11411 : 634944 , 26.59%
10.16.69.135:11411 : 530538 , 22.22%
10.10.1.228:11411 : 557532 , 23.35%
variance:0.3026909579301235
NATIVE_HASH costs:936ms, number:2387858 perdata:0.39198310787324875ns.
10.16.69.133:11411 : 209344 , 8.77%
10.16.69.135:11411 : 985967 , 41.29%
10.16.6.184:11411 : 362735 , 15.19%
10.10.1.228:11411 : 829812 , 34.75%
variance:2.0505247156316835
CRC_HASH costs:1637ms, number:2387858 perdata:0.6855516534065259ns.
10.16.69.133:11411 : 537661 , 22.52%
10.16.6.184:11411 : 581728 , 24.36%
10.16.69.135:11411 : 511612 , 21.43%
10.10.1.228:11411 : 756857 , 31.70%
variance:0.41047254512820197
FNV1_64_HASH costs:973ms, number:2387858 perdata:0.4074781666246486ns.
10.16.69.133:11411 : 607950 , 25.46%
10.16.6.184:11411 : 1144065 , 47.91%
10.16.69.135:11411 : 239652 , 10.04%
10.10.1.228:11411 : 396191 , 16.59%
variance:2.299425018737725
FNV1A_32_HASH costs:1335ms, number:2387858 perdata:0.5590784711653708ns.
10.16.69.133:11411 : 557717 , 23.36%
10.16.6.184:11411 : 729101 , 30.53%
10.16.69.135:11411 : 653616 , 27.37%
10.10.1.228:11411 : 447424 , 18.74%
variance:0.44542802226614386
實驗結論:
1、不同的伺服器ip對于每個算法的伺服器分布均勻性都有影響;
2、NATIVE_HASH受伺服器ip的影響特别大;
3、KETAMA_HASH受伺服器ip影響較小,且能保持良好的均勻性,CRC_HASH在某些情況下均勻性較好,某些情況下較差;
4、其他hash算法在各種情況下表現得均勻性都很差。
設定不同虛拟節點倍數
步驟:
1、控制虛拟節點倍數的是numReps變量,它在KetamaNodeLocatorConfiguration接口中定義,用getNodeRepetitions()方法獲得;
2、KetamaNodeLocatorConfiguration會在ConnectionFactoryBuilder進行build的時候,在createLocator方法中構造KetamaNodeLocator時被傳入KetamaNodeLocator中;
3、memcache預設使用的ConnectionFactoryBuilder會在build的時候将預設的DefaultKetamaNodeLocatorConfiguration載入KetamaNodeLocator,他的numReps預設為160且不可修改
private final int numReps = ;
4、自己編寫一個ConnectionFactoryBuilder,在build的時候,重寫createLocator方法時,傳入自己的MyKetamaNodeLocatorConfiguration,在自己的MyKetamaNodeLocatorConfiguration中重新設定numReps的值為160,320,480,640,1600,3200,對比實驗結果。
測試結果:
FNV1A_64_HASH
160:
FNV1A_64_HASH costs:1176ms, number:2387858 perdata:0.49249159707151763ns.
10.10.1.118:11411 : 555973 , 23.28%
10.16.69.133:11411 : 533208 , 22.33%
10.16.69.135:11411 : 355425 , 14.88%
10.16.6.184:11411 : 235848 , 9.88%
10.10.1.228:11411 : 346293 , 14.50%
10.10.1.208:11411 : 361111 , 15.12%
variance:0.33143952290634493
320:
FNV1A_64_HASH costs:1362ms, number:2387858 perdata:0.570385676200176ns.
10.10.1.118:11411 : 441835 , 18.50%
10.16.69.133:11411 : 480306 , 20.11%
10.16.69.135:11411 : 355425 , 14.88%
10.16.6.184:11411 : 318742 , 13.35%
10.10.1.228:11411 : 431662 , 18.08%
10.10.1.208:11411 : 359888 , 15.07%
variance:0.16774724292381052
480:
FNV1A_64_HASH costs:1241ms, number:2387858 perdata:0.5197126462293822ns.
10.10.1.118:11411 : 193664 , 8.11%
10.16.69.133:11411 : 479463 , 20.08%
10.16.69.135:11411 : 355425 , 14.88%
10.16.6.184:11411 : 373414 , 15.64%
10.10.1.228:11411 : 432505 , 18.11%
10.10.1.208:11411 : 553387 , 23.18%
variance:0.3336763701976884
640:
FNV1A_64_HASH costs:1379ms, number:2387858 perdata:0.5775050275183867ns.
10.10.1.118:11411 : 373886 , 15.66%
10.16.69.133:11411 : 479463 , 20.08%
10.16.6.184:11411 : 427466 , 17.90%
10.16.69.135:11411 : 382256 , 16.01%
10.10.1.228:11411 : 432505 , 18.11%
10.10.1.208:11411 : 292282 , 12.24%
variance:0.17161969978829905
1600:
FNV1A_64_HASH costs:1766ms, number:2387858 perdata:0.7395749663505954ns.
10.10.1.118:11411 : 545111 , 22.83%
10.16.69.133:11411 : 613142 , 25.68%
10.16.6.184:11411 : 289263 , 12.11%
10.16.69.135:11411 : 346545 , 14.51%
10.10.1.228:11411 : 446566 , 18.70%
10.10.1.208:11411 : 147231 , 6.17%
variance:0.5426740049801704
3200:
FNV1A_64_HASH costs:2211ms, number:2387858 perdata:0.9259344567390523ns.
10.10.1.118:11411 : 455113 , 19.06%
10.16.69.133:11411 : 346512 , 14.51%
10.16.69.135:11411 : 443590 , 18.58%
10.16.6.184:11411 : 389935 , 16.33%
10.10.1.228:11411 : 410865 , 17.21%
10.10.1.208:11411 : 341843 , 14.32%
variance:0.14436196587267802
FNV1_32_HASH
160:
FNV1_32_HASH costs:1205ms, number:2387858 perdata:0.5046363728496418ns.
10.10.1.118:11411 : 489055 , 20.48%
10.16.69.133:11411 : 395165 , 16.55%
10.16.69.135:11411 : 259880 , 10.88%
10.16.6.184:11411 : 232323 , 9.73%
10.10.1.228:11411 : 277434 , 11.62%
10.10.1.208:11411 : 734001 , 30.74%
variance:0.6438545073606985
320:
FNV1_32_HASH costs:1389ms, number:2387858 perdata:0.5816928812349813ns.
10.10.1.118:11411 : 489184 , 20.49%
10.16.69.133:11411 : 333188 , 13.95%
10.16.69.135:11411 : 362610 , 15.19%
10.16.6.184:11411 : 483796 , 20.26%
10.10.1.228:11411 : 350105 , 14.66%
10.10.1.208:11411 : 368975 , 15.45%
variance:0.1820378975835861
480:
FNV1_32_HASH costs:1506ms, number:2387858 perdata:0.6306907697191374ns.
10.10.1.118:11411 : 473926 , 19.85%
10.16.69.133:11411 : 319241 , 13.37%
10.16.69.135:11411 : 414314 , 17.35%
10.16.6.184:11411 : 465959 , 19.51%
10.10.1.228:11411 : 335353 , 14.04%
10.10.1.208:11411 : 379065 , 15.87%
variance:0.17289055882258353
640:
FNV1_32_HASH costs:1552ms, number:2387858 perdata:0.6499548968154722ns.
10.10.1.118:11411 : 482243 , 20.20%
10.16.69.133:11411 : 318593 , 13.34%
10.16.69.135:11411 : 445108 , 18.64%
10.16.6.184:11411 : 477512 , 20.00%
10.10.1.228:11411 : 320861 , 13.44%
10.10.1.208:11411 : 343541 , 14.39%
variance:0.20131515448144954
1600:
FNV1_32_HASH costs:1945ms, number:2387858 perdata:0.8145375478776377ns.
10.10.1.118:11411 : 392205 , 16.42%
10.16.69.133:11411 : 460475 , 19.28%
10.16.69.135:11411 : 329994 , 13.82%
10.16.6.184:11411 : 576403 , 24.14%
10.10.1.228:11411 : 278081 , 11.65%
10.10.1.208:11411 : 350700 , 14.69%
variance:0.2777437217142079
3200:
FNV1_32_HASH costs:2156ms, number:2387858 perdata:0.9029012612977824ns.
10.10.1.118:11411 : 409141 , 17.13%
10.16.69.133:11411 : 539964 , 22.61%
10.16.6.184:11411 : 280652 , 11.75%
10.16.69.135:11411 : 363105 , 15.21%
10.10.1.228:11411 : 348210 , 14.58%
10.10.1.208:11411 : 446786 , 18.71%
variance:0.22839794624712736
KETAMA_HASH
160:
KETAMA_HASH costs:2311ms, number:2387858 perdata:0.9678129939049976ns.
10.10.1.118:11411 : 411977 , 17.25%
10.16.69.133:11411 : 449525 , 18.83%
10.16.6.184:11411 : 387824 , 16.24%
10.16.69.135:11411 : 346523 , 14.51%
10.10.1.228:11411 : 382838 , 16.03%
10.10.1.208:11411 : 409171 , 17.14%
variance:0.12852730715084365
320:
KETAMA_HASH costs:2499ms, number:2387858 perdata:1.046544643776975ns.
10.10.1.118:11411 : 391581 , 16.40%
10.16.69.133:11411 : 438704 , 18.37%
10.16.6.184:11411 : 390527 , 16.35%
10.16.69.135:11411 : 348138 , 14.58%
10.10.1.228:11411 : 396903 , 16.62%
10.10.1.208:11411 : 422005 , 17.67%
variance:0.1251928291794245
480:
KETAMA_HASH costs:2526ms, number:2387858 perdata:1.0578518488117803ns.
10.10.1.118:11411 : 388526 , 16.27%
10.16.69.133:11411 : 416766 , 17.45%
10.16.6.184:11411 : 420646 , 17.62%
10.16.69.135:11411 : 368347 , 15.43%
10.10.1.228:11411 : 383291 , 16.05%
10.10.1.208:11411 : 410282 , 17.18%
variance:0.11754543766219773
640:
KETAMA_HASH costs:2587ms, number:2387858 perdata:1.0833977564830068ns.
10.10.1.118:11411 : 409084 , 17.13%
10.16.69.133:11411 : 393467 , 16.48%
10.16.6.184:11411 : 404729 , 16.95%
10.16.69.135:11411 : 377004 , 15.79%
10.10.1.228:11411 : 398191 , 16.68%
10.10.1.208:11411 : 405383 , 16.98%
variance:0.11311062154023681
1600:
KETAMA_HASH costs:2674ms, number:2387858 perdata:1.1198320838173794ns.
10.10.1.118:11411 : 393722 , 16.49%
10.16.69.133:11411 : 405244 , 16.97%
10.16.6.184:11411 : 389027 , 16.29%
10.16.69.135:11411 : 396296 , 16.60%
10.10.1.228:11411 : 415356 , 17.39%
10.10.1.208:11411 : 388213 , 16.26%
variance:0.11272230273956219
3200:
KETAMA_HASH costs:2927ms, number:2387858 perdata:1.2257847828472213ns.
10.10.1.118:11411 : 389331 , 16.30%
10.16.69.133:11411 : 397212 , 16.63%
10.16.69.135:11411 : 400242 , 16.76%
10.16.6.184:11411 : 397344 , 16.64%
10.10.1.228:11411 : 404854 , 16.95%
10.10.1.208:11411 : 398875 , 16.70%
variance:0.11148809000778596
NATIVE_HASH
160:
NATIVE_HASH costs:990ms, number:2387858 perdata:0.4145975179428592ns.
10.10.1.118:11411 : 293716 , 12.30%
10.16.69.133:11411 : 209344 , 8.77%
10.16.69.135:11411 : 694618 , 29.09%
10.16.6.184:11411 : 362735 , 15.19%
10.10.1.228:11411 : 191147 , 8.00%
10.10.1.208:11411 : 636298 , 26.65%
variance:0.7987988531108471
320:
NATIVE_HASH costs:1036ms, number:2387858 perdata:0.4338616450391941ns.
10.10.1.118:11411 : 293718 , 12.30%
10.16.69.133:11411 : 209343 , 8.77%
10.16.69.135:11411 : 694617 , 29.09%
10.16.6.184:11411 : 362735 , 15.19%
10.10.1.228:11411 : 191146 , 8.00%
10.10.1.208:11411 : 636299 , 26.65%
variance:0.7987996050576887
480:
NATIVE_HASH costs:1042ms, number:2387858 perdata:0.43637435726915086ns.
10.10.1.118:11411 : 293719 , 12.30%
10.16.69.133:11411 : 209342 , 8.77%
10.16.69.135:11411 : 694616 , 29.09%
10.16.6.184:11411 : 362735 , 15.19%
10.10.1.228:11411 : 191146 , 8.00%
10.10.1.208:11411 : 636300 , 26.65%
variance:0.7987997573996342
640:
NATIVE_HASH costs:1042ms, number:2387858 perdata:0.43637435726915086ns.
10.10.1.118:11411 : 293720 , 12.30%
10.16.69.133:11411 : 209342 , 8.77%
10.16.69.135:11411 : 694616 , 29.09%
10.16.6.184:11411 : 362735 , 15.19%
10.10.1.228:11411 : 191145 , 8.00%
10.10.1.208:11411 : 636300 , 26.65%
variance:0.7988003570512985
1600:
NATIVE_HASH costs:1097ms, number:2387858 perdata:0.4594075527104208ns.
10.10.1.118:11411 : 300948 , 12.60%
10.16.69.133:11411 : 209342 , 8.77%
10.16.69.135:11411 : 587836 , 24.62%
10.16.6.184:11411 : 375217 , 15.71%
10.10.1.228:11411 : 171437 , 7.18%
10.10.1.208:11411 : 743078 , 31.12%
variance:0.8476458026756032
3200:
NATIVE_HASH costs:1132ms, number:2387858 perdata:0.4740650407185017ns.
10.10.1.118:11411 : 300980 , 12.60%
10.16.69.133:11411 : 209342 , 8.77%
10.16.69.135:11411 : 587799 , 24.62%
10.16.6.184:11411 : 375214 , 15.71%
10.10.1.228:11411 : 171408 , 7.18%
10.10.1.208:11411 : 743115 , 31.12%
variance:0.8477000496670247
CRC_HASH
160:
CRC_HASH costs:1770ms, number:2387858 perdata:0.7412501078372332ns.
10.10.1.118:11411 : 347616 , 14.56%
10.16.69.133:11411 : 327404 , 13.71%
10.16.6.184:11411 : 459595 , 19.25%
10.16.69.135:11411 : 481764 , 20.18%
10.10.1.228:11411 : 395621 , 16.57%
10.10.1.208:11411 : 375858 , 15.74%
variance:0.1661475366273886
320:
CRC_HASH costs:1843ms, number:2387858 perdata:0.7718214399683734ns.
10.10.1.118:11411 : 291374 , 12.20%
10.16.69.133:11411 : 387281 , 16.22%
10.16.6.184:11411 : 462735 , 19.38%
10.16.69.135:11411 : 371289 , 15.55%
10.10.1.228:11411 : 489835 , 20.51%
10.10.1.208:11411 : 385344 , 16.14%
variance:0.1841338067695997
480:
CRC_HASH costs:1873ms, number:2387858 perdata:0.784385001118157ns.
10.10.1.118:11411 : 375365 , 15.72%
10.16.69.133:11411 : 362789 , 15.19%
10.16.6.184:11411 : 568127 , 23.79%
10.16.69.135:11411 : 324662 , 13.60%
10.10.1.228:11411 : 410299 , 17.18%
10.10.1.208:11411 : 346616 , 14.52%
variance:0.22471542586997548
640:
CRC_HASH costs:1904ms, number:2387858 perdata:0.7973673476396ns.
10.10.1.118:11411 : 416794 , 17.45%
10.16.69.133:11411 : 400187 , 16.76%
10.16.6.184:11411 : 539187 , 22.58%
10.16.69.135:11411 : 365325 , 15.30%
10.10.1.228:11411 : 373834 , 15.66%
10.10.1.208:11411 : 292531 , 12.25%
variance:0.20776696947943804
1600:
CRC_HASH costs:1923ms, number:2387858 perdata:0.8053242697011297ns.
10.10.1.118:11411 : 281105 , 11.77%
10.16.69.133:11411 : 365290 , 15.30%
10.16.69.135:11411 : 441715 , 18.50%
10.16.6.184:11411 : 466691 , 19.54%
10.10.1.228:11411 : 456081 , 19.10%
10.10.1.208:11411 : 376976 , 15.79%
variance:0.18471055021331423
3200:
CRC_HASH costs:1904ms, number:2387858 perdata:0.7973673476396ns.
10.10.1.118:11411 : 282749 , 11.84%
10.16.69.133:11411 : 435415 , 18.23%
10.16.69.135:11411 : 450655 , 18.87%
10.16.6.184:11411 : 486627 , 20.38%
10.10.1.228:11411 : 372277 , 15.59%
10.10.1.208:11411 : 360135 , 15.08%
variance:0.19121762886993007
FNV1_64_HASH
160:
FNV1_64_HASH costs:969ms, number:2387858 perdata:0.4058030251380107ns.
10.10.1.118:11411 : 248007 , 10.39%
10.16.69.133:11411 : 324288 , 13.58%
10.16.6.184:11411 : 1051464 , 44.03%
10.16.69.135:11411 : 239652 , 10.04%
10.10.1.228:11411 : 126840 , 5.31%
10.10.1.208:11411 : 397607 , 16.65%
variance:1.7291444612562392
320:
FNV1_64_HASH costs:1028ms, number:2387858 perdata:0.4305113620659185ns.
10.10.1.118:11411 : 248327 , 10.40%
10.16.69.133:11411 : 323947 , 13.57%
10.16.6.184:11411 : 1051144 , 44.02%
10.16.69.135:11411 : 239652 , 10.04%
10.10.1.228:11411 : 126841 , 5.31%
10.10.1.208:11411 : 397947 , 16.67%
variance:1.7277872629051703
480:
FNV1_64_HASH costs:1055ms, number:2387858 perdata:0.44181856710072376ns.
10.10.1.118:11411 : 248327 , 10.40%
10.16.69.133:11411 : 324255 , 13.58%
10.16.6.184:11411 : 1051365 , 44.03%
10.16.69.135:11411 : 239652 , 10.04%
10.10.1.228:11411 : 126841 , 5.31%
10.10.1.208:11411 : 397418 , 16.64%
variance:1.7284991720338077
640:
FNV1_64_HASH costs:1028ms, number:2387858 perdata:0.4305113620659185ns.
10.10.1.118:11411 : 248327 , 10.40%
10.16.69.133:11411 : 324377 , 13.58%
10.16.6.184:11411 : 1051245 , 44.02%
10.16.69.135:11411 : 239652 , 10.04%
10.10.1.228:11411 : 126841 , 5.31%
10.10.1.208:11411 : 397416 , 16.64%
variance:1.7279883165546042
1600:
FNV1_64_HASH costs:1045ms, number:2387858 perdata:0.43763071338412923ns.
10.10.1.118:11411 : 308326 , 12.91%
10.16.69.133:11411 : 365291 , 15.30%
10.16.6.184:11411 : 263191 , 11.02%
10.16.69.135:11411 : 504782 , 21.14%
10.10.1.228:11411 : 206764 , 8.66%
10.10.1.208:11411 : 739504 , 30.97%
variance:0.6719899505883513
3200:
FNV1_64_HASH costs:1185ms, number:2387858 perdata:0.49626066541645275ns.
10.10.1.118:11411 : 132475 , 5.55%
10.16.69.133:11411 : 509299 , 21.33%
10.16.6.184:11411 : 131879 , 5.52%
10.16.69.135:11411 : 566719 , 23.73%
10.10.1.228:11411 : 202817 , 8.49%
10.10.1.208:11411 : 844669 , 35.37%
variance:1.338157043584133
FNV1A_32_HASH
160:
FNV1A_32_HASH costs:1507ms, number:2387858 perdata:0.6311095550907968ns.
10.10.1.118:11411 : 312106 , 13.07%
10.16.69.133:11411 : 253577 , 10.62%
10.16.6.184:11411 : 644748 , 27.00%
10.16.69.135:11411 : 421664 , 17.66%
10.10.1.228:11411 : 323920 , 13.57%
10.10.1.208:11411 : 431843 , 18.08%
variance:0.3926374779645682
320:
FNV1A_32_HASH costs:1761ms, number:2387858 perdata:0.7374810394922982ns.
10.10.1.118:11411 : 400635 , 16.78%
10.16.69.133:11411 : 368357 , 15.43%
10.16.6.184:11411 : 362826 , 15.19%
10.16.69.135:11411 : 287307 , 12.03%
10.10.1.228:11411 : 410149 , 17.18%
10.10.1.208:11411 : 558584 , 23.39%
variance:0.228939842705781
480:
FNV1A_32_HASH costs:1806ms, number:2387858 perdata:0.7563263812169736ns.
10.10.1.118:11411 : 397470 , 16.65%
10.16.69.133:11411 : 369449 , 15.47%
10.16.69.135:11411 : 337365 , 14.13%
10.16.6.184:11411 : 342005 , 14.32%
10.10.1.228:11411 : 391804 , 16.41%
10.10.1.208:11411 : 549765 , 23.02%
variance:0.20084339336306026
640:
FNV1A_32_HASH costs:1812ms, number:2387858 perdata:0.7588390934469303ns.
10.10.1.118:11411 : 332503 , 13.92%
10.16.69.133:11411 : 420161 , 17.60%
10.16.69.135:11411 : 354662 , 14.85%
10.16.6.184:11411 : 346627 , 14.52%
10.10.1.228:11411 : 462565 , 19.37%
10.10.1.208:11411 : 471340 , 19.74%
variance:0.16619754052235786
1600:
FNV1A_32_HASH costs:1994ms, number:2387858 perdata:0.8350580310889508ns.
10.10.1.118:11411 : 407301 , 17.06%
10.16.69.133:11411 : 381842 , 15.99%
10.16.69.135:11411 : 335819 , 14.06%
10.16.6.184:11411 : 458970 , 19.22%
10.10.1.228:11411 : 425412 , 17.82%
10.10.1.208:11411 : 378514 , 15.85%
variance:0.13760105340499912
3200:
FNV1A_32_HASH costs:2194ms, number:2387858 perdata:0.9188151054208415ns.
10.10.1.118:11411 : 399804 , 16.74%
10.16.69.133:11411 : 397910 , 16.66%
10.16.6.184:11411 : 373879 , 15.66%
10.16.69.135:11411 : 404753 , 16.95%
10.10.1.228:11411 : 392987 , 16.46%
10.10.1.208:11411 : 418525 , 17.53%
variance:0.1142594682506669
對比結論:
1、KETAMA_HASH算法在各種情況下都有很好的均勻分布,并且倍數越高越均勻;
2、NATIVE_HASH算法不受節點倍數影響;
3、FNV1_64_HASH算法不受節點倍數影響,但在超過某段範圍之後,分布均勻性會改變;
4、FNV1_32_HASH 和 FNV1A_32_HASH随着節點倍數增加,均勻性會變好;
5、FNV1A_64_HASH 和 CRC_HASH 随節點倍數增加波動性很大;
算法原理(160倍率、640适用)
NATIVE_HASH
1、hash是取字元串的hashcode,
2、這樣虛拟節點的最後hash落位基本都在一起,虛拟節點穿插分布的作用并沒有起到,相同節點的虛拟節點基本都分布在一起,相當于沒有用到虛拟節點,
3、最終伺服器區間的分布也不均勻。
CRC_HASH
1、取CRC32并右移16位;
2、會發生虛拟節點落位沖突的情況,後面的将前面的直接覆寫(CRC32本身就有碰撞機率);
3、會散亂分布。
相關連結:
http://xdxd.love/2016/01/14/CRC32算法詳解和使用場景/
https://blog.csdn.net/yunhua_lee/article/details/42775039
http://preshing.com/20110504/hash-collision-probabilities/
http://www.backplane.com/matt/crc64.html
FNV HASH算法:
FNV1_64_HASH:虛拟節點集中分布,無沖突覆寫
FNV1A_64_HASH:虛拟節點略有分散但是還是聚集分布,無沖突覆寫
FNV1_32_HASH:虛拟節點集中分布,無沖突覆寫
FNV1A_32_HASH:虛拟節點略有打亂,無沖突覆寫
https://blog.csdn.net/fall221/article/details/8291381
KETAMA_HASH
1、根據key取MD5得到16位字元數組,
2、将16位字元數組相鄰4位倒序拼裝成hash,一次得到四個虛拟節點hash,
3、最終虛拟節點hash分布穿插錯落且分布區間比較均勻,無沖突覆寫。
問題與思考
原來的hash算法是将叢集中的ip對應上一個點,每個機器ip對應上hash結果的一個點(比如8台機器,進行模7運算,将0-7對應的hash結果分别配置設定給8台機器),這樣其實可以減少節點(比如第七台機器下線了,配置設定的hash值為6,則可以讓第八台機器負擔流量,接收6,7的hash結果),但是增加節點的話配置設定不夠了(比如增加了一台機器9,但是hash結果隻有八個,不能區分出流量分給他,則必須重新定義hash的模數)
一緻性hash是将hash結果集取得很大(0~2^32),然後将機器ip也取模,最後落在結果集上,将結果集劃分成區間,按照區間配置設定給各個機器,這樣機器減少時還是一樣,隻是新負擔的機器接管了區間,而在增加的時候,因為是劃分了區間,是以可以對區間再進行劃分,從原區間中劃分出來一部分分給新機器就可以了(其實就是新機器算一次ip的hash,将上一個節點的ip hash結果到新節點的ip hash結果這段區間分給新機器)
用戶端沒有存儲key和host的map,而是存儲了伺服器虛拟節點的區間分布情況,存儲在ketamaNodeLocator類中的ketamaNodes中,這是一個TreeMap結構,每次存儲時,都根據要存儲的key計算hash,然後在ketamaNodes中找到對應應該存儲的節點。