【问题标题】:PHP Generate Unique Order Number with DatePHP 生成带有日期的唯一订单号
【发布时间】:2014-04-12 07:34:12
【问题描述】:

我想生成以下 12 位数字格式的唯一标识符:

YYYYMMDDXXXX

例子:

201403052318

地点:

YYYYMMDD 是当前日期值,其他 XXXX 是随机生成的值。

$today = date("Ymd");
$rand = sprintf("%04d", rand(0,9999));
$unique = $today . $rand;

每日所需的唯一数量约为 100。我应该使用哪些 PHP 方法来防止 rand 值可能重复或使所有 id 最大唯一?也许可以使用当前时间函数将这些数字压缩到最后 4 个字符中?

编辑: 作为表的主要索引连接到 MySQL 数据库的唯一值。它是初始值,未连接到数据库中的任何存储信息。

【问题讨论】:

  • 是否涉及数据库?您是否尝试最初创建一个随机数数组(不重复)并在其他地方使用它?您打算如何访问此脚本?通过 CLI 还是通过 HTTP 请求?请为您的问题添加更多详细信息以获得更准确的答案。
  • 你真的需要一个随机数还是只是一些伪唯一的东西?
  • 伪唯一,是否可以将小时-分钟-秒压缩为最后 4 个字符以逃避随机?
  • @KenTang,然后你可以有你的$rand这样的变量..$rand = strtoupper(substr(uniqid(sha1(time())),0,4));

标签: php date time format


【解决方案1】:

您不能依赖 rand() ,您可能会生成副本(rand(0,9999) 生成副本的情况很少见,但在某些时候会这样)。

因此,不要使用rand(),只需创建一个增量值(例如,从 1 开始)并附加到您生成的日期。

下次当您重新生成一个新 id 时,获取该增量值(例如,如果您将其存储在某个地方.. 必须是 1 对吗?)状态,增加它并将其附加到您的新日期。

不是一个理想的解决方案..(欢迎批评)

您可以使用uniqidsha-1time 结合使用,并对它们的前4 个字符执行substr()

<?php
$today = date("Ymd");
$rand = strtoupper(substr(uniqid(sha1(time())),0,4));
echo $unique = $today . $rand;

OUTPUT :

201403094B3F

【讨论】:

  • 这个答案很好,但很少见?您必然会在 10,000 个样本中生成一个副本,而且可能比这更快更多。想想生日悖论。此外,最好添加一条关于捕获该计数器溢出并处理它的评论。
【解决方案2】:

我需要做类似的事情,一个既能保持时间又能保持 id 唯一性的解决方案,我最终得到了一个使用 PHP function time() 的解决方案,就像这样

$reference_number = 'BFF-' . time();您可以将BFF 更改为对您的业务逻辑更有意义的内容。

我的唯一参考 id 看起来像 BFF-1393327176,并且该数字可以从 Unix 转换为实时数字,这将为您提供 Tue, 25 Feb 2014 11:19:36

希望对你有帮助

【讨论】:

    【解决方案3】:

    如果唯一值生成一次,您只需对 rand 值进行条件选择并将值存储在将成为条件的数组中 -使用inarray-:

    $amount = 100; // the amount of ids
    $previousValues = array();
    for ($i = 0; $i < $amount; $i++){    
        $rand = rand(0,9999);
        while (in_array($rand, $previousValues)){
            $rand = rand(0, 9999);
        }
        $previousValues[] = $rand;
        $today = date("Ymd");
        $unique = $today.$rand;
        echo $unique."\n";
    }
    

    结帐this demo

    【讨论】:

      【解决方案4】:

      创建唯一“唯一订单号”的可能解决方案如下,我假设您有 orders 表和字段 order_number,那么代码是:

      $orderNumber = DB::table('orders')->max('order_number') + random_int(10, 100);
      

      如果将第一个订单编号插入为“100000000000”,该方法将为您提供以下编号:

      100000000025
      100000000056
      100000000089
      100000000123
      100000000199
      100000000232
      100000000249
      

      使用这种方法,非唯一数字是不可能的,但缺点是每个数字都大于前一个数字(不是 100% 随机),但这种方法在大多数情况下是可以接受的。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2018-09-01
        • 1970-01-01
        • 1970-01-01
        • 2019-09-29
        • 2023-04-03
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多