Mysql 从id号生成唯一序列号

Mysql 从id号生成唯一序列号,mysql,Mysql,我有一个增量增加id的数据库。我需要一个函数,将该id转换为0到1000之间的唯一数字。(实际最大值要大得多,但只是为了简单起见。) 生成的编号不能重复。 它不能是增量的。 需要动态生成它(而不是创建一个统一的数字表来读取) 我认为这是一个散列函数,但有可能发生冲突。 随机数也可能有重复项。 我需要一个最小完美散列函数,但找不到一个简单的解决方案。它似乎不必是数字?MD5散列呢 从…中选择md5(id+rand(10000))因为标准有点模糊(足以愚弄普通人),我不确定该走哪条路。以下是一些想法

我有一个增量增加id的数据库。我需要一个函数,将该id转换为0到1000之间的唯一数字。(实际最大值要大得多,但只是为了简单起见。)

生成的编号不能重复。 它不能是增量的。 需要动态生成它(而不是创建一个统一的数字表来读取)

我认为这是一个散列函数,但有可能发生冲突。 随机数也可能有重复项。
我需要一个最小完美散列函数,但找不到一个简单的解决方案。

它似乎不必是数字?MD5散列呢


从…中选择md5(id+rand(10000))

因为标准有点模糊(足以愚弄普通人),我不确定该走哪条路。以下是一些想法:

  • 你可以用一个小盒子。根据维基百科页面:

    给定一个小的特权输入集(例如,编译器的保留字),可以调整排列表,使这些输入产生不同的散列值,产生所谓的完美散列函数

  • 你可以使用一个看起来很复杂的一对一的数学函数。这样做的缺点是,由于一对一的要求,很难做出不严格增加或严格减少的。如果您执行了类似于
    (id^2)+id*2
    的操作,则id之间的间隔将发生变化,并且在不知道原始id的情况下,无法立即看出函数是什么

  • 你可以这样做:

    new_id = (old_id << 4) + arbitrary_4bit_hash(old_id);
    

    当然,这种情况会发生,因为对于较小的数字,所有较高的位都是0,所以map函数相当于移位。这就是为什么我建议对数字的低位使用伪随机数据,而不是高位。这会使规律的间隔不那么明显。为了帮助缓解这个问题,我编写的函数只移动前3位,旋转其余的。通过这样做,对于所有大于7的ID,规则间隔将不那么明显。

    如果将0到1000之间的数字转换为另一组0到1000之间的数字,您将任意地将一个数字映射到另一个数字。增量ID有什么问题?这正是我需要做的。。。从一个集合转换到另一个集合,但我不知道一个简单的函数来实现这一点。之所以需要转换id,是因为我的老板想创建一个网站,用这个唯一的id搜索数据库。他认为,如果人们知道它是增量的,他们可以增量搜索数据库中的每个项目。人们不能找到所有项目有多重要?如果使用某种散列函数,则可能有人发现该散列函数,然后以任何方式递增搜索。为了使这实际上是加密安全的,你要么生成一些随机的东西并存储它,要么用别人无法获得的密钥加密ID。我同意,但这是他想要的。每个id的形式都是01-****,起初我只是将数字转换成十六进制,比如01-0002af,但他认为从这个数字开始计数太容易了。它不一定是超级安全的,我猜他认为普通人不会尝试破解散列。但是可能的碰撞呢。他提到了这一点。好吧-所以留下rand()-我真的不知道ist,但是MD5是否应该达到一个非常高的数字?可能是唯一的。如果不明确地检查它们,我就不会依赖它。我真的很喜欢选项2和3。其他人创造了太多的角色。我仍然面临的问题是射程。如果我有1000个id,我需要将每个id映射到[0,1000]范围内的唯一序列。选项2和3都会创建更大的数字。我可以只制作一个表,并将0到1000进行混合,但我更愿意在运行时生成它们。似乎应该有一个简单的函数来实现这一点。也许把所有的位子向左推,把最远的位子向左旋转到最左边。例如100101到001011。“但我如何才能做到这一点呢?”约翰贝克说,这要看情况而定。“你想用什么语言来表达?”约翰贝克我编辑了我的答案。因为函数使用二进制运算,所以范围是0-1024,而不是0-1000。可以吗?对不起,实际上是0-1023是的,这很有帮助,我想这可能是我会选择的。我会推高你的评论,但我是新来的堆栈溢出,所以我不允许你。谢谢大家
    new_id = (old_id << 4) + arbitrary_4bit_hash(old_id);
    
    function map($number)
    {
        // Shift the high bits down to the low end and the low bits
        // down to the high end
        // Also, mask out all but 10 bits. This allows unique mappings
        // from 0-1023 to 0-1023
        $high_bits = 0b0000001111111000 & $number;
        $new_low_bits = $high_bits >> 3;
        $low_bits =  0b0000000000000111 & $number;
        $new_high_bits = $low_bits << 7;
        // Recombine bits
        $new_number = $new_high_bits | $new_low_bits;
        return $new_number;
    }
    
    function demap($number)
    {
        // Shift the high bits down to the low end and the low bits
        // down to the high end
        $high_bits = 0b0000001110000000 & $number;
        $new_low_bits = $high_bits >> 7;
        $low_bits =  0b0000000001111111 & $number;
        $new_high_bits = $low_bits << 3;
        // Recombine bits
        $new_number = $new_high_bits | $new_low_bits;
        return $new_number;
    }
    
    map(1) * 2 == map(2)
    map(1) * 3 == map(3)