在我的用户数据库表中,我将用户电子邮件地址的MD5散列作为id。
示例:email(example@example.org) = id(d41d8cd98f00b204e9800998ecf8427e)
不幸的是,我现在必须将id表示为整数值--以便能够使用id只能为整数的API。
现在我正在寻找一种方法来将id编码成一个整数,以便在接收时再次解码。我该怎么做呢?
我目前的想法是:
convert_uuencode()
和convert_uudecode()
用于MD5哈希
1.将MD5散列的每个字符替换为其ord()
值
哪种方法更好?你知道更好的方法吗?
我希望你能帮助我。先谢谢你!
9条答案
按热度按时间xxslljrj1#
要小心。将MD5转换为整数需要支持big(128位)整数。很有可能你使用的API只支持32位整数--或者更糟,可能处理浮点数。无论哪种方式,你的ID都会被删除。如果是这种情况,与试图将MD5转换为整数相比,仅任意分配第二个ID是更好的处理方式。
然而,如果你确信API可以处理任意大的整数,你可以把MD5从十六进制转换成整数,PHP很可能不支持这个内置函数,因为它会试图把它表示成32位整数或浮点数;您可能需要使用PHP GMP library。
tmb3ates2#
其他人指出,以不同的方式这样做是有充分理由的。
但是如果你想把一个md5哈希转换成一个 * 十进制数字串 *(我认为这就是你所说的"用整数表示"的真正含义,因为md5已经是一个字符串形式的整数了),然后再把它转换回同样的md5字符串:
演示:
当然,使用这两个字符串都要小心,比如确保只将它们用作字符串类型以避免丢失前导零,确保字符串的长度正确等等。
7qhs6swi3#
一个简单的解决方案可以通过指定base 16作为第二个参数来使用
intval()
。支持64位整数的系统可以将128位/16字节的
md5()
散列拆分为两个8字节的部分,然后进行转换。每个十六进制对代表1个字节,因此在本例中使用16个字符的块:对于32位整数,十六进制块为8个字符:
q9rjltbz4#
为什么ord()?md5生成的是16字节的值,为了更好的可读性,它是以十六进制的形式呈现的。所以你不能将16字节的值转换成4或8字节的整数。你必须修改你的算法的某些部分,才能将其用作id。
rsl1atfo5#
您可以使用hexdec来解析十六进制字符串并将数字存储在数据库中。
w1jd8yoj6#
你不能添加另一个自动递增的整型字段吗?
k2fxgqgv7#
关于:
或
碰撞的机会肯定更大,但仍然很好,足以使用,而不是散列在数据库虽然?
mbzjlibv8#
将这两列添加到表中。
在这两列上创建一个PK可能会有帮助,也可能没有帮助,因为它可能会连接两个字符串表示并散列结果。这可能会挫败你的目的,完全扫描可能会更快,但这取决于列数和记录数。不要试图在php中读取这些bigint,因为它没有无符号整数,只是停留在SQL中,并执行如下操作:
MD5确实会碰撞btw。
9rnv2umw9#
使用电子邮件地址作为共享文件夹(如/var/myprocess/ www.example.com)中的空临时文件的文件名example@example.org
然后,对文件名调用ftok。ftok将返回一个唯一的整数ID。
虽然不能保证它是唯一的,但它可能足以满足您的API。