一致性Hash算法

2023-11-04

原文:https://www.cnblogs.com/lpfuture/p/5796398.html

一致性Hash算法背景

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

  但现在一致性hash算法在分布式系统中也得到了广泛应用,研究过memcached缓存数据库的人都知道,memcached服务器端本身不提供分布式cache的一致性,而是由客户端来提供,具体在计算一致性hash时采用如下步骤:

  1. 首先求出memcached服务器(节点)的哈希值,并将其配置到0~232的圆(continuum)上。
  2. 然后采用同样的方法求出存储数据的键的哈希值,并映射到相同的圆上。
  3. 然后从数据映射到的位置开始顺时针查找,将数据保存到找到的第一个服务器上。如果超过232仍然找不到服务器,就会保存到第一台memcached服务器上。

 

  从上图的状态中添加一台memcached服务器。余数分布式算法由于保存键的服务器会发生巨大变化而影响缓存的命中率,但Consistent Hashing中,只有在园(continuum)上增加服务器的地点逆时针方向的第一台服务器上的键会受到影响,如下图所示:

 

一致性Hash性质

  考虑到分布式系统每个节点都有可能失效,并且新的节点很可能动态的增加进来,如何保证当系统的节点数目发生变化时仍然能够对外提供良好的服务,这是值得考虑的,尤其实在设计分布式缓存系统时,如果某台服务器失效,对于整个系统来说如果不采用合适的算法来保证一致性,那么缓存于系统中的所有数据都可能会失效(即由于系统节点数目变少,客户端在请求某一对象时需要重新计算其hash值(通常与系统中的节点数目有关),由于hash值已经改变,所以很可能找不到保存该对象的服务器节点),因此一致性hash就显得至关重要,良好的分布式cahce系统中的一致性hash算法应该满足以下几个方面:

  • 平衡性(Balance)

平衡性是指哈希的结果能够尽可能分布到所有的缓冲中去,这样可以使得所有的缓冲空间都得到利用。很多哈希算法都能够满足这一条件。

  • 单调性(Monotonicity)

单调性是指如果已经有一些内容通过哈希分派到了相应的缓冲中,又有新的缓冲区加入到系统中,那么哈希的结果应能够保证原有已分配的内容可以被映射到新的缓冲区中去,而不会被映射到旧的缓冲集合中的其他缓冲区。简单的哈希算法往往不能满足单调性的要求,如最简单的线性哈希:x = (ax + b) mod (P),在上式中,P表示全部缓冲的大小。不难看出,当缓冲大小发生变化时(从P1到P2),原来所有的哈希结果均会发生变化,从而不满足单调性的要求。哈希结果的变化意味着当缓冲空间发生变化时,所有的映射关系需要在系统内全部更新。而在P2P系统内,缓冲的变化等价于Peer加入或退出系统,这一情况在P2P系统中会频繁发生,因此会带来极大计算和传输负荷。单调性就是要求哈希算法能够应对这种情况。

  • 分散性(Spread)

在分布式环境中,终端有可能看不到所有的缓冲,而是只能看到其中的一部分。当终端希望通过哈希过程将内容映射到缓冲上时,由于不同终端所见的缓冲范围有可能不同,从而导致哈希的结果不一致,最终的结果是相同的内容被不同的终端映射到不同的缓冲区中。这种情况显然是应该避免的,因为它导致相同内容被存储到不同缓冲中去,降低了系统存储的效率。分散性的定义就是上述情况发生的严重程度。好的哈希算法应能够尽量避免不一致的情况发生,也就是尽量降低分散性。

  • 负载(Load)

负载问题实际上是从另一个角度看待分散性问题。既然不同的终端可能将相同的内容映射到不同的缓冲区中,那么对于一个特定的缓冲区而言,也可能被不同的用户映射为不同的内容。与分散性一样,这种情况也是应当避免的,因此好的哈希算法应能够尽量降低缓冲的负荷。

  • 平滑性(Smoothness)

平滑性是指缓存服务器的数目平滑改变和缓存对象的平滑改变是一致的。

原理

基本概念

  一致性哈希算法(Consistent Hashing)最早在论文《Consistent Hashing and Random Trees: Distributed Caching Protocols for Relieving Hot Spots on the World Wide Web》中被提出。简单来说,一致性哈希将整个哈希值空间组织成一个虚拟的圆环,如假设某哈希函数H的值空间为0-2^32-1(即哈希值是一个32位无符号整形),整个哈希空间环如下:

  整个空间按顺时针方向组织。0和232-1在零点中方向重合。

  下一步将各个服务器使用Hash进行一个哈希,具体可以选择服务器的ip或主机名作为关键字进行哈希,这样每台机器就能确定其在哈希环上的位置,这里假设将上文中四台服务器使用ip地址哈希后在环空间的位置如下:

  

接下来使用如下算法定位数据访问到相应服务器:将数据key使用相同的函数Hash计算出哈希值,并确定此数据在环上的位置,从此位置沿环顺时针“行走”,第一台遇到的服务器就是其应该定位到的服务器。

  例如我们有Object A、Object B、Object C、Object D四个数据对象,经过哈希计算后,在环空间上的位置如下:

根据一致性哈希算法,数据A会被定为到Node A上,B被定为到Node B上,C被定为到Node C上,D被定为到Node D上。

下面分析一致性哈希算法的容错性和可扩展性。现假设Node C不幸宕机,可以看到此时对象A、B、D不会受到影响,只有C对象被重定位到Node D。一般的,在一致性哈希算法中,如果一台服务器不可用,则受影响的数据仅仅是此服务器到其环空间中前一台服务器(即沿着逆时针方向行走遇到的第一台服务器)之间数据,其它不会受到影响。

下面考虑另外一种情况,如果在系统中增加一台服务器Node X,如下图所示:

此时对象Object A、B、D不受影响,只有对象C需要重定位到新的Node X 。一般的,在一致性哈希算法中,如果增加一台服务器,则受影响的数据仅仅是新服务器到其环空间中前一台服务器(即沿着逆时针方向行走遇到的第一台服务器)之间数据,其它数据也不会受到影响。

综上所述,一致性哈希算法对于节点的增减都只需重定位环空间中的一小部分数据,具有较好的容错性和可扩展性。

另外,一致性哈希算法在服务节点太少时,容易因为节点分部不均匀而造成数据倾斜问题。例如系统中只有两台服务器,其环分布如下,

此时必然造成大量数据集中到Node A上,而只有极少量会定位到Node B上。为了解决这种数据倾斜问题,一致性哈希算法引入了虚拟节点机制,即对每一个服务节点计算多个哈希,每个计算结果位置都放置一个此服务节点,称为虚拟节点。具体做法可以在服务器ip或主机名的后面增加编号来实现。例如上面的情况,可以为每台服务器计算三个虚拟节点,于是可以分别计算 “Node A#1”、“Node A#2”、“Node A#3”、“Node B#1”、“Node B#2”、“Node B#3”的哈希值,于是形成六个虚拟节点:

同时数据定位算法不变,只是多了一步虚拟节点到实际节点的映射,例如定位到“Node A#1”、“Node A#2”、“Node A#3”三个虚拟节点的数据均定位到Node A上。这样就解决了服务节点少时数据倾斜的问题。在实际应用中,通常将虚拟节点数设置为32甚至更大,因此即使很少的服务节点也能做到相对均匀的数据分布。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

一致性Hash算法 的相关文章

随机推荐

  • Go语言实现Onvif客户端:7、获取摄像头快照

    Go语言实现Onvif客户端 7 获取摄像头快照 文章目录 Go语言实现Onvif客户端 7 获取摄像头快照 1 代码 2 结果 3 查看 1 代码 摄像头对该时刻可以进行快照抓拍 抓拍结果可以以url地址的形式提供 在浏览器上可以直接查看
  • python/函数

    Python 函数 函数是组织好的 可重复使用的 用来实现单一 或相关联功能的代码段 函数能提高应用的模块性 和代码的重复利用率 你已经知道Python提供了许多内建函数 比如print 但你也可以自己创建函数 这被叫做用户自定义函数 定义
  • 2021-05-26

    import org apache flink api common functions RichMapFunction import org apache flink statefun flink core StatefulFunctio
  • 到底什么是数据中台?

    最近可能大家听到 数据中台 这个词越来越频繁了 有时候我跟一些朋友聊起来 也是都在说这个 但是一直不知道这到底是个什么 最近就看到这篇文章 觉得说的还挺好的 分享给大家看看 希望大家看完能对数据中台有一些认识 转载来源 公众号 AI 前线
  • 【面向对象】多态类继承

    package TcmStudy day26 public class Test01 public static void main String args Cat c1 new Cat 子类对象初始化 实例化子类对象 创建一个父类类型对象
  • 7.2-C 标准库的实现

    复习 sh xv6 c 仅依赖系统调用的 最小 命令行 Shell 本次课回答的问题 Q 如何在系统调用之上构建程序能够普遍受惠的标准库 本次课主要内容 C 标准库设计与实现 基于 libc 的应用程序 一 熟悉又陌生的 libc 为什么需
  • Python基本操作

    前言 啦啦啦 现在开始 打算做一期Python基础教程 欢迎大家来看哦 导读 这期文章真的是Python基础中的基础 相信有一定编程基础的小伙伴们都一定能看懂的 本文共分为以下几个部分 数与运算符 基本输入输出 注释 模块基本操作 小彩蛋
  • Blob总结

    Blob Blob表示二进制类型的大对象 在数据库管理系统中 将二进制数据存储为一个单一个体的集合 Blob 对象表示一个不可变 原始数据的类文件对象 Blob 表示的不一定是JavaScript原生格式的数据 File 接口基于Blob
  • 磁盘性能测试工具-FIO的安装及使用

    文章目录 FIO介绍 FIO安装 在线安装 离线安装 磁盘测试 命令行方式 测试结果说明 命令参数说明 配置文件方式 dd命令介绍 使用方法 FIO介绍 FIO是一款测试IOPS的工具 用于对磁盘进行压力测试和验证 磁盘I O是检查磁盘性能
  • Arcpy(二)逐要素批量裁剪矢量数据集

    文章目录 一 前言 1 1 需求 1 2 实现思路 二 代码 2 1 导入库 2 2 设置文件夹路径并获取图幅编号 2 3 逐图幅批量裁剪 2 4 删除空要素类 三 小结 参考资料 一 前言 1 1 需求 现有一个较大区域的地形图数据集 矢
  • Android性能测试

    Android应用性能测试 Android用户也许会经常碰到以下的问题 1 应用后台开着 手机很快没电了 应用耗电大 2 首次 非首次启动应用 进入应用特别慢 应用启动慢 3 应用使用过程中 越来越卡 CPU能力不足 内存泄露 4 应用页面
  • JavaScript---DOM对象

    文章目录 JavaScript DOM对象 一 操作DOM对象 1 1 DOM对象的核心 1 2 获得DOM节点 1 3 更新DOM节点 1 4 删除DOM节点 1 5 插入DOM节点 1 6 创建一个新标签 实现插入 1 7 insert
  • Intro to Java Programming(Liang.10th)--02

    Chapter2 2 2 Writing a simple program ComputeArea concatenate strings 2 3 Reading input form Console How to specific imp
  • hive sql/ spark sql/sql 根据时间取最新的记录

    取用户购买的最新时间 套餐 价格等 由于用户购买的套餐类型多 导致求出来的是各个套餐的最新时间 但是我只要用户购买时间最新的一个套餐 直接select userid max time product from 表 group by user
  • C语言课程设计之设计菜单程序

    C语言课程设计之设计菜单程序 设计要求 1 菜单内容 程序运行后 给出三个菜单选项的内容和输入提示 1 FindNum 2 Dimand 3 Goodbye Input 1 3 2 设计要求 使用1 3数字来选择菜单项 其他输入则不起作用
  • 【剑指offer】数据结构——字符串

    目录 数据结构 字符串 直接解 剑指offer 05 替换空格 剑指offer 17 打印从1到最大的n位数 剑指offer 20 表示数值的字符串 剑指offer 37 序列化二叉树 剑指offer 50 第一个只出现一次的字符 剑指of
  • CUDA笔记

    1 cudaDeviceSynchronize 用于CPU和GPU同步 即cpu和GPU均运行至cudaDeviceSynchronize 后再继续 CPU多线程时 会阻止所有线程 2 syncthreads 用于核函数内线程块线程同步 即
  • Cygwin配置优化(乱码、颜色等问题)

    前面介绍了如何将Cygwin集成到Windows资源管理器的右键菜单中 点击在当前路径下打开窗口 本文介绍一些乱码问题与美化问题 1 乱码问题 在Cygwin中执行Windows原生程序 如ping ipconfig 时会出现中文乱码 显示
  • 遗传算法与TSP问题

    一 遗传算法 遗传算法 Genetic Algorithm 是模拟达尔文生物进化论的自然选择和遗传学机理的生物进化过程的计算模型 是一种通过模拟自然进化过程搜索最优解的方法 遗传算法是从代表问题可能潜在的解集的一个种群 population
  • 一致性Hash算法

    原文 https www cnblogs com lpfuture p 5796398 html 一致性Hash算法背景 一致性哈希算法在1997年由麻省理工学院的Karger等人在解决分布式Cache中提出的 设计目标是为了解决因特网中的