当我们要将一个庞大的数据进行编号时,而编号有位数限制,比如5位的车牌号、10位的某证件号码、订单流水号、短网址等等,我们可以使用36进制计算出符合位数的不重复的编号。

下载:https://url72.ctfile.com/f/17999272-578149816-47e65a?p=7793 (访问密码:7793)

我们将0-Z(0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ)分别代表数值0-35,如字母Z代表35。这样的话我要得到一个5位的编号,最大信息量就是36的5次方了,36^5 = 60466176,即最大的5位编号相当于10进制的数字:60466176。

本文中为了做演示,我们假定某俱乐部发放一批10位的会员卡号,会员卡号由3位城市编号+5位卡号编码+2位校验码组成。城市编号用区号表示,如755代表深圳,5位卡编号则由36进制的卡编号组成,后面两位校验码则是通过一定的算法生成的,校验码的用处是可以验证卡号的合法性。这样的话,我们生成的10位卡号相当于最大能满足6000多万会员卡号,并且是不重复唯一的卡号。

我们使用PHP进行进制转换,10进制转36进制。

 1 class Code {
2 //密码字典
3 private $dic = array(
4 0=>'0', 1=>'1', 2=>'2', 3=>'3', 4=>'4', 5=>'5', 6=>'6', 7=>'7', 8=>'8',
5 9=>'9', 10=>'A', 11=>'B', 12=>'C', 13=>'D', 14=>'E', 15=>'F', 16=>'G', 17=>'H',
6 18=>'I',19=>'J', 20=>'K', 21=>'L', 22=>'M', 23=>'N', 24=>'O', 25=>'P', 26=>'Q',
7 27=>'R',28=>'S', 29=>'T', 30=>'U', 31=>'V', 32=>'W', 33=>'X', 34=>'Y', 35=>'Z'
8 );
9
10
11 public function encodeID($int, $format=8) {
12 $dics = $this->dic;
13 $dnum = 36; //进制数
14 $arr = array ();
15 $loop = true;
16 while ($loop) {
17 $arr[] = $dics[bcmod($int, $dnum)];
18 $int = bcdiv($int, $dnum, 0);
19 if ($int == '0') {
20 $loop = false;
21 }
22 }
23 if (count($arr) < $format)
24 $arr = array_pad($arr, $format, $dics[0]);
25
26 return implode('', array_reverse($arr));
27 }
28
29 public function decodeID($ids) {
30 $dics = $this->dic;
31 $dnum = 36; //进制数
32 //键值交换
33 $dedic = array_flip($dics);
34 //去零
35 $id = ltrim($ids, $dics[0]);
36 //反转
37 $id = strrev($id);
38 $v = 0;
39 for ($i = 0, $j = strlen($id); $i < $j; $i++) {
40 $v = bcadd(bcmul($dedic[$id {
41 $i }
42 ], bcpow($dnum, $i, 0), 0), $v, 0);
43 }
44 return $v;
45 }
46
47 }

我们定义Code类,先定义密码字典,即0-Z分别对应的数值,方法encodeID($int, $format)中参数$int表示数字,$format表示位数长度,比方encodeID(123456789,5)表示将数字123456789转换成5位的36进制编号,而方法decodeID($ids)用于将36进制的编号转换成10进制的编号。

我们可以这样来生成卡号:

$code = new Code();
$card_no = $code->encodeID(888888,5);

如上,我们就可以得到一个5位的卡编号,它实际代表着卡号是888888(6个8)的会员编号,而实际进行转换后是5位编号:0J1VC。

接着,我们将城市编号和校验码加上,城市编号是已经定义好的,校验码则通过一定的算法取得,本例中,我们使用简单的算法:将前三位城市编号和五位卡编号进行md5加密,然后取md5值的前2位作为校验码,这样就得到了编号后面的两位校验码。

1 $card_pre = '755';
2 $card_vc = substr(md5($card_pre.$card_no),0,2);
3 $card_vc = strtoupper($card_vc);
4 echo $card_pre.$card_no.$card_vc;

实际应用中,可以通过数据库得到10进制的编号,保证编号唯一,再将上述代码组合,最终生成一个10位的不重复的卡号。

PHP生成唯一不重复的编号的更多相关文章

  1. C#生成唯一不重复订单号帮助类

    1.使用场景 通常,在做一些表单的功能时,需要生成唯一不重复的订单单号,本文提供的帮助类可以适合大多数场景的单号生成使用,拿来即用,方便快捷无重复.而且,在高并发的情况下也是可以使用的. 之前看到有人 ...

  2. PHP实现生成唯一编号(36进制的不重复编号)

    当我们要将一个庞大的数据进行编号时,而编号有位数限制,比如5位的车牌号.10位的某证件号码.订单流水号.短网址等等,我们可以使用36进制计算出符合位数的不重复的编号. 我们将0-Z(012345678 ...

  3. 如何生成唯一的server Id,server_id为何不能重复?

    我们都知道MySQL用server-id来唯一的标识某个数据库实例,并在链式或双主复制结构中用它来避免sql语句的无限循环.这篇文章分享下我对server-id的理解,然后比较和权衡生成唯一serve ...

  4. java生成唯一的id编号

    GUID是一个128位长的数字,一般用16进制表示.算法的核心思想是结合机器的网卡.当地时间.一个随即数来生成GUID.从理论上讲,如果一台机器每秒产生10000000个GUID,则可以保证(概率意义 ...

  5. java 生成20位唯一ID,生成不会重复的20位数字----https://blog.csdn.net/weixin_36751895/article/details/70331781

    java 生成20位唯一ID,生成不会重复的20位数字----https://blog.csdn.net/weixin_36751895/article/details/70331781

  6. 生成唯一的id(转)

    很多朋友都利用md5()来生成唯一的编号,但是md5()有几个缺点:1.无序,导致数据库中排序性能下降.2.太长,需要更多的存储空间.其实PHP中自带一个函数来生成唯一的id,这个函数就是uniqid ...

  7. 用SQL存储过程生成唯一单据号

    用SQL存储过程生成唯一单据号     在一些系统中,经理要生成单据号,为了不使多台客户端生成的单据号重复,一般要在服务端生成这种流水号,本文是在数据库中生成流水号,并且可以生成多种类型的单据号(比如 ...

  8. php 生成唯一id的几种解决方法

    php 生成唯一id的几种解决方法   网上查了下,有很多的方法 1.md5(time() . mt_rand(1,1000000)); 这种方法有一定的概率会出现重复 2.php内置函数uniqid ...

  9. js 如何生成唯一且不可预测的 ID

    通常数据库可以生成唯一的 ID,最多的就是数字序列,也有像 MongoDB 这样产生组合序列的,不过这种形式的 ID 由于是序列,是可以预测的.如果想得到不可预测且唯一的 ID,方法还是有的. 下面主 ...

随机推荐

  1. 用Typescript 的方式封装Vue3的表单绑定,支持防抖等功能。

    Vue3 的父子组件传值.绑定表单数据.UI库的二次封装.防抖等,想来大家都很熟悉了,本篇介绍一种使用 Typescript 的方式进行统一的封装的方法. 基础使用方法 Vue3对于表单的绑定提供了一 ...

  2. SAP 日期计算

    1. CONVERSION_EXIT_IDATE_OUTPUT     INPUT:      20200601     OUTPUT:   03FEB2008 2. CONVERT_DATE_TO_ ...

  3. UiPath图片操作截图的介绍和使用

    一.截图(Take Screenshot)的介绍 截取指定的UI元素屏幕截图的一种活动,输出量仅支持图像变量(image) 二.Take Screenshot在UiPath中的使用 1. 打开设计器, ...

  4. 集合容器和Hash表

    集合容器 集合相当于一个容器,在我们使用Arraylist的时候添加参数相当与放了一个容器中.这里面的元素是可以重复的 在HashSet中添加元素是没有重复的,我们来写一个测试看一下 public s ...

  5. java面向对象编程---方法

    二.方法 1.方法的重载 1.1 方法的签名 方法的唯一标识就是方法的签名:方法的名字和参数列表: 一个类中不能出现两个方法的签名完全一样的方法 1.2 方法的重载 方法名相同但参数列表不同称之为方法 ...

  6. 研发效能生态完整图谱&DevOps工具选型必看

    本文主要梳理了研发效能领域完整的方向图谱以及主流工具,其中对少部分工具也做了一些点评.看了之后,大家可以对研发效能这个领域有个整体认识,同时研发效能落地的时候也有对应的工具(黑话叫抓手)可以选择. 我 ...

  7. 聊一聊 C# 后台GC 到底是怎么回事?

    一:背景 写这一篇的目的主要是因为.NET领域内几本关于阐述GC方面的书,都是纯理论,所以懂得人自然懂,不懂得人也没法亲自验证,这一篇我就用 windbg + 源码 让大家眼见为实. 二:为什么要引入 ...

  8. 【Go语言】(一)环境搭建与了解VScode工具

    视频链接(p1~p8): golang入门到项目实战 [2022最新Go语言教程,没有废话,纯干货!] 参考链接: 用vscode开发go的时候,安装go包报错:connectex: A connec ...

  9. python 操作xml、html文件

    简介 在一些项目中可能会使用到解析html文件,尤其是爬虫相关的,需要解析获取到的html内容,通常我们会使用lxml模块去进行html文件的解析. html文件 当前存在一个简单的html < ...

  10. Modbus转OPC

    在这里给大家介绍一种低成本的将Modbus RTU协议的串口设备接入到OPC UA的服务器呢? OPC全称是OLE(Object Linking and Embedding) for Process ...