了解散列算法的位和字节

问题描述

在关于一个非常简单的哈希算法 djb2 的 question 中,作者想知道为什么在算法中选择数字 33(参见下面的 C 代码)。

unsigned long;
hash(unsigned char *str)
{
    unsigned long hash = 5381;
    int c;

    while (c = *str++) //just the character
        hash = ((hash << 5) + hash) + c; /* hash * 33 + c */

    return hash;
}

在最上面的答案中,第 2 点谈到了哈希累加器以及它如何制作自己的两个副本,然后它谈到了传播。

谁能解释一下“复制自身”和答案 2 的“传播”是什么意思?

解决方法

作为参考的第 2 步是这样的:

  1. 正如您从移位和加法实现中看到的那样,使用 33 会生成散列累加器中大部分输入位的两个副本,然后将这些位分散得相对较远。这有助于产生良好的雪崩。使用较大的移位会复制较少的位,使用较小的移位会使位交互更加局部化,并使交互传播所需的时间更长。

33 是 32+1。这意味着,由于乘法是可分配的,hash * 33 = (hash * 32) + (hash * 1) - 或者换句话说,制作 hash 的两个副本,将其中一个左移 5 位,然后将它们加在一起,这就是 {{ 1}} 以更直接的方式表达。