一致性Hash(基于google Guava实现)


背景

一般我们使用的hash就是md5 sha 之类的工具类,在负载均衡会要求类似同一个ip在增加节点时还是定位到之前的节点,这时就要用到一致性hash。具体实现代码参考(基于google Guava):

使用谷歌 Guava 实现 Java 一致性哈希 (用于根据哈希Hash值平均分配的场景)​my.oschina.net图标

一、介绍

MurmurHash算法:高运算性能,低碰撞率,由Austin Appleby创建于2008年,现已应用到Hadoop、libstdc++、nginx、libmemcached等开源系统。2011年Appleby被Google雇佣,随后Google推出其变种的CityHash算法。

Java界中Redis,Memcached,Cassandra,HBase,Lucene都用它。

在Java的实现,Guava的Hashing类里有,上面提到的Jedis,Cassandra里都有Util类。

但存在的问题是由于Java的数据类型long与C语言中无符号长整型uint64_t有区别,导致Java输出版本存在负数,针对这个问题进行了修改;另外需要注意的是中文不同编码(UTF-8或GBK)会导致输出结果的不同,使用中需要统一编码。

 

p.s.一致性hash的实现算法,murmurhash和ketamahash。下面这篇文章有详细的说明。

浅析ketamahash和murmurhash - 程序诗人 - 博客园​www.cnblogs.com

二、原理

 

 

算法图例

 

 

三、性能测试对比

import java.nio.charset.StandardCharsets; import org.apache.commons.codec.digest.DigestUtils; import com.google.common.hash.Hashing; public class Test { public static void main(String[] args) { System.out.println(murmur3Test("334324324234234sfsfsdfwwrtregreg")); long startTime=System.currentTimeMillis(); for (int i = 0; i < 10000000; i++) { Test.md5Test("KFETHGRETWERFSDFWEFWEFWF"); } long endTime=System.currentTimeMillis(); System.out.println("1000万次md5Test算法程序运行时间: " + (endTime - startTime ) + "ms"); long startTime2=System.currentTimeMillis(); for (int i = 0; i < 10000000; i++) { Test.murmur3Test("KFETHGRETWERFSDFWEFWEFWF"); } long endTime2=System.currentTimeMillis(); System.out.println("1000万次murmur3Test算法程序运行时间: " + (endTime2 - startTime2 ) + "ms"); } public static String murmur3Test(String primaryKey) { return Hashing.murmur3_32().hashString(primaryKey, StandardCharsets.UTF_8).toString() + "_" + primaryKey; } public static String md5Test(String primaryKey) { return DigestUtils.md5Hex(primaryKey)+ "_" + primaryKey; } }


结论:

MurmurHash算法比md5快一倍。

四、使用场景

1、根据uuid,通过hash算法进行取模分库分表

2、用来计算出key的slot值

3、短链接

五、其他算法

ketamahash一致性哈希算法

由若干固定的虚拟节点来计算出每个虚拟节点的slots,数据存储的时候,算出key的slot值,然后存入相邻最近的虚拟节点

 

转载
hash函数MurmurHash_luoqinglong的专栏-CSDN博客​blog.csdn.net图标

 

 


免责声明!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系本站邮箱yoyou2525@163.com删除。



 
粤ICP备18138465号  © 2018-2025 CODEPRJ.COM