为固定长度输入创建一个快速哈希函数

3

目前我正在处理一个项目,其中一些信息需要进行哈希。由于数据集非常庞大(每天创建数百万条记录),因此数据转换算法必须快速。

需要哈希的数据块是固定长度的(11个十进制数字 - 例如:05018144298)。因此,我想知道是否值得创建自己的哈希函数,而不是使用一些现有的函数(例如MD5),以显著减少处理时间。如果确实如此,那么最好的方法是什么?是否可以修改某些现有算法(例如MD5,但将输入分成较小的块并修改其他参数以适应11位十进制数字的固定输入),还是最好从头设计哈希函数?

谢谢!


4
为什么要对这些值进行哈希处理?换句话说,你是使用哈希来加速查找(例如哈希表)还是试图为每个值创建几乎唯一的摘要值? - Steven Sudit
1
你希望哈希结果有多小?考虑到输入只有11个字节,所以你希望得到什么样的结果呢?或者你是说有11个单独的值? - PaulG
请参见:http://stackoverflow.com/questions/3635738/how-to-create-a-hash-function-to-mask-confidential-informations - Steven Sudit
“每天数百万次”并不意味着您需要特别快。每天1千万个哈希意味着您有8.64毫秒的时间用于每个哈希 - 即使是昂贵的哈希函数也足够了。 - Nick Johnson
1
@niko:你得到的关于性能的建议是非常正确的:哈希是快速的,所以加速它几乎没有什么好处。此外,由于生日悖论,即使是完美的哈希,如果它对于你输入的数据量不够宽,仍然会产生许多冲突。 - Steven Sudit
显示剩余2条评论
3个回答

4
  1. 在实际测量使用现有哈希函数是否确实具有非常重要的影响之前,性能方面做任何事情都不值得。在典型PC上,典型的MD5实现将能够每秒处理数百万个小消息,仅使用主CPU上的单个核心。你“每天数百万次”的机会是小菜一碟。

  2. 设计自己的哈希函数,同时保持哈希函数的安全特性,是一个非常糟糕的想法。目前,全球顶级密码学家正在参与由NIST组织的公开竞赛设计新的标准哈希函数。数十名非常专业的研究人员已经研究了几年,并将继续进行约两年的研究。一个孤立的程序员,对这个主题不是很专业,在几天或几周内试图做得更好,几乎是荒谬的。设计安全的哈希函数很困难。

对于您来说,正确的做法是使用现有的标准加密哈希函数。顺便说一下,那不是MD5;该函数已经发现了严重的弱点(实际上,自1996年以来已经发现了严重的弱点,并且在过去15年中未推荐使用MD5)。最好使用SHA-256。

如果您不需要哈希函数的加密属性,而只需要类似散列表索引的随机化函数,则任何哈希函数都足够好。只需进行分析,注意没有性能问题,并感到高兴即可。


1
关于性能和不重复造轮子的建议是非常正确的。至于仅用于良好分布的哈希,事实证明任何加密哈希都具有出色的分布性,但许多非加密哈希则存在问题。 - Steven Sudit
MD5已知的弱点是碰撞攻击,而不是预像攻击,因此不要轻易地忽略MD5。 - Jason S

2
不要尝试创建自己的哈希或加密算法。如果你不是这个领域的专家,你很可能会搞砸它。使用一个现有的算法,由真正知道他们在做什么的人开发,由知道他们在做什么的人实现,经过试验和测试的算法。
话虽如此,我不清楚你想哈希什么:
如果它是一个具有11位数字的单个数字,你可以将该数字存储在64位整数(在C中为long long int)中。将该数字视为已经是哈希值是否可行?
如果它是一个包含11个元素的集合,例如11个32位数字,则使用像MD5、SHA-1或者你喜欢的任何算法等现有算法,该算法由你的系统支持,例如OpenSSL。OpenSSL还支持利用专用的加密芯片和CPU扩展(如所有MMX变体,甚至专门用于加速算法的AES扩展),因此速度不应该成为问题。

1

如果您的目标是隐藏个人身份信息(例如电话号码、社会安全号码等),那么哈希不是一个很好的解决方案。它总是容易受到彩虹表攻击,而且(正如其他人已经非常清楚地指出的那样)依赖于您自己开发的某些私有哈希函数将无法提供任何安全性。

制作一次性密码本(OTP)。这只是一个以个人身份识别号码为键的表格,第二列包含相同格式的随机数字。使用加密安全的 Windows CSP 或类似工具随机生成第二列,并由于定义在其上的唯一索引而保证其唯一性。

使用 OTP 将所有个人身份识别号码的实例替换为相应的随机等价物。完成后,丢弃 OTP。

此时,没有存储的秘密可以危及数据的隐私。事实上,您能够找出随机数对应的原始数据的唯一方法是拥有所有原始数据,即使这也不是轻松的事情。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接