consistent hashing 算法的原理

consistent hashing 是一种 hash 算法,简单的说,在移除 / 添加一个 cache 时,它能够尽可能小的改变已存在key 映射关系,尽可能的满足单调性的要求。

下面就来按照 5 个步骤简单讲讲 consistent hashing 算法的基本原理。

1 环形hash 空间

考虑通常的 hash 算法都是将 value 映射到一个 32 为的 key 值,也即是 0~2^32-1 次方的数值空间;我们可以将这个空间想象成一个首( 0 )尾( 2^32-1 )相接的圆环,如下面图 1 所示的那样。

图 1 环形 hash 空间

2 把对象映射到hash 空间

接下来考虑 4 个对象 object1~object4 ,通过 hash 函数计算出的 hash 值 key 在环上的分布如图 2 所示。

hash(object1) = key1;

… …

hash(object4) = key4;

图 2 4 个对象的 key 值分布

3 把cache 映射到hash 空间

Consistent hashing 的基本思想就是将对象和 cache 都映射到同一个 hash 数值空间中,并且使用相同的 hash算法。

假设当前有 A,B 和 C 共 3 台 cache ,那么其映射结果将如图 3 所示,他们在 hash 空间中,以对应的 hash 值排列。

hash(cache A) = key A;

… …

hash(cache C) = key C;

图 3 cache 和对象的 key 值分布

说到这里,顺便提一下 cache 的 hash 计算,一般的方法可以使用 cache 机器的 IP 地址或者机器名作为 hash输入。

4 把对象映射到cache

现在 cache 和对象都已经通过同一个 hash 算法映射到 hash 数值空间中了,接下来要考虑的就是如何将对象映射到 cache 上面了。

在这个环形空间中,如果沿着顺时针方向从对象的 key 值出发,直到遇见一个 cache ,那么就将该对象存储在这个 cache 上,因为对象和 cache 的 hash 值是固定的,因此这个 cache 必然是唯一和确定的。这样不就找到了对象和 cache 的映射方法了吗?!

依然继续上面的例子(参见图 3 ),那么根据上面的方法,对象 object1 将被存储到 cache A 上; object2 和object3 对应到 cache C ; object4 对应到 cache B ;

5 考察cache 的变动

前面讲过,通过 hash 然后求余的方法带来的最大问题就在于不能满足单调性,当 cache 有所变动时, cache会失效,进而对后台服务器造成巨大的冲击,现在就来分析分析 consistent hashing 算法。

5.1移除 cache

考虑假设 cache B 挂掉了,根据上面讲到的映射方法,这时受影响的将仅是那些沿 cache B 逆时针遍历直到下一个 cache ( cache C )之间的对象,也即是本来映射到 cache B 上的那些对象。

因此这里仅需要变动对象 object4 ,将其重新映射到 cache C 上即可;参见图 4 。

图 4 Cache B 被移除后的 cache 映射

5.2添加 cache

再考虑添加一台新的 cache D 的情况,假设在这个环形 hash 空间中, cache D 被映射在对象 object2 和object3 之间。这时受影响的将仅是那些沿 cache D 逆时针遍历直到下一个 cache ( cache B )之间的对象(它们是也本来映射到 cache C 上对象的一部分),将这些对象重新映射到 cache D 上即可。

因此这里仅需要变动对象 object2 ,将其重新映射到 cache D 上;参见图 5 。

图 5 添加 cache D 后的映射关系

虚拟节点

考量 Hash 算法的另一个指标是平衡性 (Balance) ,定义如下:

平衡性

平衡性是指哈希的结果能够尽可能分布到所有的缓冲中去,这样可以使得所有的缓冲空间都得到利用。

hash 算法并不是保证绝对的平衡,如果 cache 较少的话,对象并不能被均匀的映射到 cache 上,比如在上面的例子中,仅部署 cache A 和 cache C 的情况下,在 4 个对象中, cache A 仅存储了 object1 ,而 cache C 则存储了object2 、 object3 和 object4 ;分布是很不均衡的。

为了解决这种情况, consistent hashing 引入了“虚拟节点”的概念,它可以如下定义:

“虚拟节点”( virtual node )是实际节点在 hash 空间的复制品( replica ),一实际个节点对应了若干个“虚拟节点”,这个对应个数也成为“复制个数”,“虚拟节点”在 hash 空间中以 hash 值排列。

仍以仅部署 cache A 和 cache C 的情况为例,在图 4 中我们已经看到, cache 分布并不均匀。现在我们引入虚拟节点,并设置“复制个数”为 2 ,这就意味着一共会存在 4 个“虚拟节点”, cache A1, cache A2 代表了 cache A ; cache C1, cache C2 代表了 cache C ;假设一种比较理想的情况,参见图 6 。

图 6 引入“虚拟节点”后的映射关系

此时,对象到“虚拟节点”的映射关系为:

objec1->cache A2 ; objec2->cache A1 ; objec3->cache C1 ; objec4->cache C2 ;

因此对象 object1 和 object2 都被映射到了 cache A 上,而 object3 和 object4 映射到了 cache C 上;平衡性有了很大提高。

引入“虚拟节点”后,映射关系就从 { 对象 -> 节点 } 转换到了 { 对象 -> 虚拟节点 } 。查询物体所在 cache 时的映射关系如图 7 所示。

图 7 查询对象所在 cache

“虚拟节点”的 hash 计算可以采用对应节点的 IP 地址加数字后缀的方式。例如假设 cache A 的 IP 地址为202.168.14.241 。

引入“虚拟节点”前,计算 cache A 的 hash 值:

Hash(“202.168.14.241”);

引入“虚拟节点”后,计算“虚拟节”点 cache A1 和 cache A2 的 hash 值:

Hash(“202.168.14.241#1”);  // cache A1

Hash(“202.168.14.241#2”);  // cache A2

一致性hash算法虚拟节点_一致性hash和虚拟节点相关推荐

  1. hash oracle 分表_一致性Hash算法在数据库分表中的实践

    最近有一个项目,其中某个功能单表数据在可预估的未来达到了亿级,初步估算在90亿左右.与同事详细讨论后,决定采用一致性Hash算法来完成数据库的自动扩容和数据迁移.整个程序细节由我同事完成,我只是将其理 ...

  2. 一致性hash算法虚拟节点_一致性哈希算法——虚拟节点

    一致性哈希算法--虚拟节点 一致性哈希算法是分布式系统中常用的算法.比如,一个分布式的存储系统,要将数据存储到具体的节点上,如果采用普通的hash方法,将数据映射到具体的节点上,如key%N,key是 ...

  3. 一致性hash算法虚拟节点_一致性Hash算法原理详解

    数据分片 先让我们看一个例子吧: 我们经常会用 Redis 做缓存,把一些数据放在上面,以减少数据的压力. 当数据量少,访问压力不大的时候,通常一台Redis就能搞定,为了高可用,弄个主从也就足够了: ...

  4. 一致性hash算法虚拟节点_一致性 Hash 算法

    一致性哈希算法在1997年由麻省理工学院提出,设计目标是为了解决因特网中的热点(Hot spot)问题,初衷和CARP十分类似.一致性哈希修正了CARP使用的简单哈希算法带来的问题,使得DHT可以在P ...

  5. 一致性hash算法虚拟节点_一致性哈希虚拟节点

    采用固定哈希算法平衡负载 在大规模的缓存应用中,应运而生了分布式缓存系统.key-value如何均匀的分散到集群中?最常规的方式莫过于hash取模的方式.比如集群中可用机器适量为N,那么key值为K的 ...

  6. java 一致性hash算法 均衡分发_负载均衡-基础-一致性哈希算法及java实现

    1 /** 2 * 一致性hash 的java 实现3 *@authorluoqiang4 * @data 2016/11/085 */ 6 public classConsistencyHash { ...

  7. java 一致性hash算法 均衡分发_Dubbo一致性哈希负载均衡的源码和Bug,了解一下?...

    本文是对于Dubbo负载均衡策略之一的一致性哈希负载均衡的详细分析.对源码逐行解读.根据实际运行结果,配以丰富的图片,可能是东半球讲一致性哈希算法在Dubbo中的实现最详细的文章了. 文中所示源码,没 ...

  8. 安卓平板隐藏虚拟按键_实现安卓设备虚拟按键隐藏和显示的方法和系统的制作方法...

    实现安卓设备虚拟按键隐藏和显示的方法和系统的制作方法 [技术领域] [0001]本发明涉及移动终端显示技术领域,尤其涉及一种方便实现安卓设备虚拟按键隐藏和显示的方法和系统. [背景技术] [0002] ...

  9. hash oracle 分表_数据库hash分表

    前言 平常我们一直用的就是按时间进行分表,按时间分表可以减轻以时间维度的查询.但是如果查询的条件不是时间,那么当查询主表的时候,就会去遍历所有的分表,没有起到分表的优化效果. 方法 如果不能按照时间分 ...

最新文章

  1. voc格式的图片训练集相对普通训练集有何优点?
  2. 驱动程序实例(四):按键驱动程序(platform + input子系统 + 外部中断方式)
  3. go 语言 mysql_Go语言基础之操作MySQL
  4. ArcGIS实验教程——实验二十七:时态数据可视化----以飓风路径为例
  5. java实现可选形参_Java:可选的可选实现
  6. 当集合a为空集时a的取值范围_高中数学必修一第一章集合分节练习和章末测试题含答案[1] 2...
  7. 公司管理项目管理中的技巧
  8. android蓝牙设置名称流程,Android 8 设置蓝牙名称 流程
  9. 漫话:如何给女朋友解释华为鸿蒙OS是怎样实现跨平台的?
  10. 【BZOJ3207】花神的嘲讽计划Ⅰ Hash+主席树
  11. slam的回顾(一)
  12. ecshop php7 mysql_ecshop如何修改并支持PHP7
  13. 我的世界Java版最诡异的种子_我的世界:MC出现诡异的种子,地域不停地重复
  14. matlab网格划分提取坐标,ANSYS-划分网格后导出单元和结点坐标等信息
  15. 数字电子技术课程设计报告——电子脉搏测试仪的设计
  16. 【雕爷学编程】Arduino动手做(43)---单路继电器模块
  17. 2022-06-清华管理学-清华大学-宁向东
  18. 前端基础第一天:HTML常用标签知识点
  19. java 构造方法能被继承吗_Java中构造函数可以被继承么
  20. 如何做好描述统计分析?

热门文章

  1. 卫片执法-外业核查已上传照片下载
  2. 让微积分穿梭于工作与学习之间(10):在椭圆弧上做匀速运动,我就无能为力了
  3. ROS2机器人笔记21-02-23
  4. T(n) = 25T(n/5)+n^2的时间复杂度,笔试啊笔试!
  5. 痞子衡嵌入式:轻松为i.MXRT设计更新Segger J-Link Flash下载算法文件
  6. GPT分区安装windows10详细教程
  7. leecode++理解
  8. 抓取今日头条的个人收藏夹目录
  9. Linux运维常用命令汇总
  10. 【java基础】史上最详细的配置环境变量步骤