雪花算法

应用场景

集群高并发情况下生成全局唯一id

1. id 生成规则的硬性要求:

  1. 全局唯一
  2. 趋势递增
  3. 单调递增
  4. 信息安全
  5. 含事件戳

2. id号生成系统的可用性要求:

  1. 高可用
  2. 低延迟
  3. 高并发

  3. 生成全局唯一的id主流方案

    1. UUID   为什么无序的UUID 会导致入库性能变差呢?

    • 分布式id一般都会作为主键,但是MYSQL官方推荐主键越短越好
    • UUID无序,作为主键会导致索引分裂,大大降低索引的性能。

      数据库自增id 在分布式里面,数据库的自增id机制的原理是:数据库自增id和mysql的replace into 实现的(没有新增有则替换,字段创建唯一索引),缺点:系统水平扩展困难。

      redis单线程天生保证原子性,可以使用原子操作incr和incr by 来实现

      redis 集群情况下,需要设置不同的步长,同时key一定要设置有效期,通过redis集群来获取更高的吞吐量。 (强烈不推荐入库)

    2. 雪花算法 Twitter的snowflake用糊涂工具包

1. 为什么叫雪花算法

在大自然中几乎找不出两朵完全相同的雪花。(这么说,这个算法还是很牛逼)

2. 组成

41位时间戳 + 10 位机器ID + 12位序号(自增),转换成长度为18的长整型。

雪花算法会生成一个64位的二进制数据,为一个Long型。(转换成字符串后长度最多19)

一个可能会重复的数 + 一个永远不可能重复的数 = 永远不可能重复的数

 

      • 为什么 1bit 是无意义

          因为二进制里第一个 bit 为如果是 1,那么都是负数,但是我们生成的 id 都是正数,所以第一个 bit 统一都是 0。

      • 41 bit 时间戳 ,单位是毫秒

          41 bit 可以表示的数字多达 2^41 - 1,也就是可以标识 2 ^ 41 - 1 个毫秒值,换算成年就是表示 69 年的时间。

      • 10 bit:记录工作机器id,代表的是个服务最多可以部署在2 ^ 10 台机器上,也就是1024 台机器。

          但是10 bit 里面5个bit代表机房id,5个bit代表机器id。意思就是最多代表 2 ^ 5 个机房(32个机房),每个机房里面可以代表2^5个机器(32台机器),这里可以随意拆分,比如拿出4位标识业务号,其他6位作为机器号。可以随意组合。

      • 12 bit: 这个是用来记录同一个毫秒内产生的不同id。

           12 bit 可以代表的最大正整数是 2 ^ 12 -1 = 4096,也就是说可以用这个12bit 代表的数字来区分同一个毫秒内的4096个不同的id。也就会是同一毫秒内同一台机器所生成的最大ID数量为4096。

posted @ 2021-02-02 20:43  恰恰的故事  阅读(604)  评论(0编辑  收藏  举报