文档章节

使用hilo高低位算法-生成编号

6pker
 6pker
发布于 2016/02/01 14:29
字数 490
阅读 826
收藏 6

通常订单编号、产品编号、付款编号等编号,都是由数字构成,有得会加一些前缀后缀,例如淘宝订单号。

下面说一下几点不合理的编号设计。

  1. 使用数字型的自增长、序列。这用来表示唯一性没问题,但是当我们遇到像订单编号这种,需要一定长度不太合适。

  2. 编号需要一定长度,可能你会想到uuid。uuid生成的包含字符,无序、无意义而且也比较长,不符合我们的写记习惯,所以uuid做编号也是不合理的。

  3. 使用时间戳来当编号,在并发的情况下精确到毫秒也有可能发生唯一性问题

  4. 使用随机数加前后缀当编号,很多语言的随机数都是伪随机,例如用java每次都new Random(),并发的情况下有可能取出一样的数字,就算不并发,谁能保证不会随机到之前生成过的数字?


合理的做法是用表来管理数字主键,每次取出来拼接前缀或后缀来当编号,然后+1,就像oracle的序列一样,因为有些数据库没有序列,所以通常为了统一使用表来管理。

private class HiloOptimizer {

        private String prefix;
        private int maxLo;
        private int lo;            
        private long hi;        
        private long lastValue;

        public HiloOptimizer(String prefix, int maxLo) {
            this.prefix = prefix != null ? prefix.replace("{", "${") : "";
            this.maxLo = maxLo;            //最大低位
            this.lo = maxLo + 1;           //最低初始位
        }

        public synchronized String generate() {
            if (lo > maxLo) {                    //当低位超过最大高位
                lastValue = getLastValue();  //表示hi位的进位次数,从数据库id管理表获取
                lo = lastValue == 0 ? 1 : 0;     //低位归0
                hi = lastValue * (maxLo + 1);    //高位进位
            }
            return String.valueOf(hi + lo++);    //低位最后自增lo++
        }
    }

若maxLo设置为99,按照hi的每次进位划分,产生的id形式是:

0~99,100~199,200~299,300~399……依此类推,每个阶段99+1个


© 著作权归作者所有

共有 人打赏支持
6pker
粉丝 52
博文 97
码字总数 59252
作品 0
浦东
程序员
私信 提问
hilo高低位算法的优点和用途(非Hibernate主键策略)

开门见山地说,hilo高低位算法的用途,或者说目前为止我所见过的用途,就是——编号生成! 通常订单编号、产品编号、物流编号、工人编号、批次编号等等各种各样的编号,都是由数字构成,有得...

Awisper
2015/12/17
1K
0
Hibernate的generator属性之意义【转】

Hibernate的generator属性之意义 本文讲述Hibernate的generator属性的意义。Generator属性有7种class,本文简略描述了这7种class的意义和用法。 Hibernate的Generator属性有7种class,本文简...

houyiwujing
2012/02/28
0
0
Hibernate的generator属性的意义

本文讲述Hibernate的generator属性的意义。Generator属性有7种class,本文简略描述了这7种class的意义和用法。 Hibernate的Generator属性有7种class,本文简略描述了这7种class的意义和用法。...

黄梦巍
2013/06/26
0
0
常用Hibernate 主键生成策略

ORM映射基本原理 1. 基于相同实体类和表,实现相互映射,类的对象对应了表中的记录,不同对象对应不同的记录,不同的记录对应不同的对象 2. 表中不同的记录通过主键来区分,不同的对象通过对...

徐文瑞
2013/03/09
0
1
4.01-Hibernate中主键生成的策略

1)identity:主键自增,由数据库来生成主键, 在我们创建实体时,不需要手动添加主键,而是由数据库自动生成主键 2)increment:主键自增,有hibernate来维护(生成),先通过查询数据库中主...

静以修身2025
2017/11/14
0
0

没有更多内容

加载失败,请刷新页面

加载更多

nginx中部署vue打包后的静态文件

如何在nginx中部署静态资源就不描述了, 请看我的这篇博客 将vue脚手架项目打包后的静态文件放到nginx上, 发现有个问题, 即url上有#, 怎么去掉这个#呢. 1 项目中router的mode 路由的mode要为h...

克虏伯
16分钟前
4
0
JS容易理解错误的地方

在这端代码执行的末尾,你会不会hi变量回事函数中的hi了?你会不会认为这不是按引用传递了? 对值传递和引用传递产生质疑了? 1 var hi = {};2 function sayHello(hi) { ...

器石_
17分钟前
2
0
Java开发学习--MongoDB

之前只学过sql,第一次使用非关系型数据库。以前对于关系型数据库与非关系型数据库的概念很模糊,通过这次的学习对这两者有了一个清晰的概念。 主键 在MongoDB中,主键名叫"_id",如果在生成...

微笑向暖wx
21分钟前
0
0
Java8-2-Lambda表达式实战-一句话实现Map中按照Value排序

今天我们来实战一把, 对Map的Value值排序进行简化. 如果想学习Java工程化、高性能及分布式、深入浅出。微服务、Spring,MyBatis,Netty源码分析的朋友可以加我的Java高级交流:854630135,群...

编程SHA
24分钟前
0
0
Vue中img的src属性绑定与static文件夹

1、其中有一个叫做static的文件夹,尝试将logo.png放入这个文件夹,然后修改imgUrl: imgUrl = '/static/logo.png' 成功读取到了logo.png. 执行npm run build后查看dist文件,发现logo.png原...

小黑202
25分钟前
0
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部