一致性 hash 算法
hash的意思是散列,目的将一组输入的数据均匀的分开、打散。可以实现快速的查找,插入,删除等操作。在很多工具和程序都能看到,比如:map的key,负载均衡,数据分片,数据统计等等。
一致性hash:对节点和数据,都做一次hash运算,然后比较节点和数据的hash值,数据值和节点最相近的节点作为处理节点。为了分布得更均匀,通过使用虚拟节点的方式,每个节点计算出n个hash值,均匀地放在hash环上这样数据就能比较均匀地分布到每个节点。
原理:
对于一个圆形的环分割成2^32份,也就是0到2^32-1的空间,然后在这个圆形的空间均匀的分布所有的服务器。比如有三个服务器就分成三份。按照顺时针的方向,每个服务器只管理自己顺时针上的区域,那么就可以管理这个园上所有区域的数据就分别存储到三个服务器上。理论上很完美的实现了hash值和服务器的关系。下图说明:
上面的CacheA,CacheB,CacheC这是三个服务器。如果计算的对象对应的hash值刚好这三个服务器,直接就可以取到服务器。如果就像图中Object1对应的hash值key1不在服务器,按照顺时针的方向,找到cacheA,说明Object1对象在CacheA存储着,同理Object4在CacheB上。
实际物理节点:
图中有三个服务器,对应三个物理节点,每个节点按理想情况下负载压力差不多。一切看起来那么完美,但是,如果CacheB服务器挂掉,按照顺时针的方法,Object4就会找到CacheC上,这样CacheC就会承担2\3的压力,也就是CacheC的压力是cacheA的两倍。也会出现数据迁移的,导致原先圆环的数据重新分配到CacheA和CacheB上。这样很容易出现问题。这些下面的出现解决方案!
虚拟物理节点:
如果上图的服务器的每个虚拟出5个节点,这样就有原先的3个服务器变成15个服务器,然后把这15个服务器在通过hash运算放到这个环上,这样就会出现均匀的计算,比如:CacheA&&VN1,CacheC&&VN1,CacheB&&VN4,CacheA&&VN5,CacheB&&VN2,CacheC&&VN4...,这样的数据,这样如果CacheB挂掉,那么CacheB的下一个可能是A,也可能是C,这样就会分担一部分压力,不出现一个服务瞬时压力变大。
添加虚拟节点的java代码:
评论 (1 条评论)