为什么'397'用于ReSharper GetHashCode覆盖?

pro*_*mer 145 resharper hash hash-code-uniqueness

像许多人一样,我使用ReSharper来加速开发过程.当您使用它来覆盖类的相等成员时,它为GetHashCode()生成的代码生成如下所示:

    public override int GetHashCode()
    {
        unchecked
        {
            int result = (Key != null ? Key.GetHashCode() : 0);
            result = (result * 397) ^ (EditableProperty != null ? EditableProperty.GetHashCode() : 0);
            result = (result * 397) ^ ObjectId;
            return result;
        }
    }
Run Code Online (Sandbox Code Playgroud)

当然我有一些自己的成员,但我想知道的是为什么397?

  • 编辑:所以我的问题会更好措辞,因为它是一个特殊的关于397素数除了它是素数?

Nic*_*son 159

可能是因为397是足够大的素数,导致结果变量溢出并稍微混合散列的位,从而提供更好的散列码分布.没有什么特别的关于397将它与其他相同数量的素数区分开来.

  • 并且397很高兴.难道我们都不想快乐吗? (70认同)
  • 正如尼克所说,没有什么特别之处.它不需要那个大小,这只是一个足够大的数字,当你计算一个哈希时,结果会溢出(因为GetHashCode()返回一个Int32).选择素数只对分布有帮助,我没有数学学位,所以我不打算尝试解释它,但乘以素数会产生比任何其他任意数乘以更好分布的结果. (5认同)
  • 好吧,但为什么它必须是素数,为什么它必须具有那么精确的幅度?如果它必须是素数,为什么不2或2147483647?我想要得到很好的突变(这个乘法的唯一原因就是突变)我们不需要数字作为素数.我们需要乘数器具有相对相同的数字或0和1,最好没有明确的模式.397 = 110001101b符合.仍然不确定幅度. (2认同)

Nic*_*ver 17

Ben是正确的,反映大会你可以看到它只是他们选择使用的素数.

  • asm:`JetBrains.ReSharper.Feature.Services.CSharp`方法:`CSharpEqualityHelper.GenerateGetHashCodeBody` (10认同)
  • 哪个组装? (9认同)

kyb*_*kos 13

resharper使用的哈希看起来像FNV哈希的变体.FNV经常用不同的素数实现.有一个关于素数FNV选用合适的讨论在这里.