std :: hash保证在stdlib发行版中是相同的

Mat*_*son 10 c++ hash c++11 stdhash

如果我std::hash使用了libstdc++,然后在即将推出的C++11VS 2012库中做了一个- 它们会匹配吗?

我假设哈希实现不是C++规范的一部分,可以根据分布而变化?

use*_*136 9

不,这不能保证.std::hash只需要遵守以下条件:

  1. 接受Key类型的单个参数.
  2. 返回size_t类型的值,该值表示参数的哈希值.
  3. 调用时不抛出异常.
  4. 对于两个相等的参数k1和k2,std :: hash()(k1)== std :: hash()(k2).
  5. 对于不相等的两个不同参数k1和k2,std :: hash()(k1)== std :: hash()(k2)的概率应该非常小,接近1.0/std :: numeric_limits :: max ().

http://en.cppreference.com/w/cpp/utility/hash

  • 虽然cppreference是一个很好的网站(我自己一直使用它),但它并不等同于标准. (2认同)

Kil*_*nDS 9

标准只说这个:

20.8.12类模板散列23.5中定义的无序关联容器使用类模板散列的特化作为默认散列函数.对于所有对象类型存在特化散列的密钥,实例化散列应:

  • 满足Hash要求(17.6.3.4),Key作为函数调用参数类型,DefaultConstructible要求(表19),CopyAssignable要求(表23),
  • 对于左值,可以交换(17.6.3.2)
  • 提供两个嵌套类型result_type和argument_type,它们分别是size_t和Key的同义词,
  • 满足以下要求:如果k1 == k2为真,则h(k1)== h(k2)也为真,其中h是类型为散列的对象,k1和k2是Key类型的对象.

在17.6.3.4中,这是最重要的(表26):

不要抛出异常.返回的值仅取决于参数k.[注意:因此,对于具有相同k值的表达式h(k)的所有评估产生相同的结果. - 结束注释] [注意:对于两个不同的值t1和t2,h(t1)和h(t2)比较的概率应该非常小,接近1.0/numeric_- limits :: max(). - 结束说明]

所以一般来说,不,计算本身没有定义,结果不需要在实现上保持一致.就此而言,即使同一个库的两个不同版本也可能会产生不同的结果.


eca*_*mur 5

函数返回的值的要求(17.6.3.4哈希要求[hash.requirements])Hash是:

表26 - 哈希要求[哈希]

返回的值仅取决于参数k.[注意:因此,对h(k)具有相同值的表达式的所有评估k产生相同的结果.- 注意事项] [注意:对于两个不同的值,t1并且t2,h(t1)h(t2)等于的概率 应该非常小,接近1.0 / numeric_limits<size_t>::max(). - 尾注]

在实践中,对于整数类型std::hash(k)来说,这是很常见的k,因为这是符合标准的最简单的可能实现.对于其他类型,一切皆有可能.