当前位置: 首页 > 知识库问答 >
问题:

定义哈希函数的C++20概念

糜野
2023-03-14

在cppreference上,有一个示例定义了概念hashable。我复制了下面的示例:

template<typename T>
concept Hashable = requires(T a) {
    { std::hash<T>{}(a) } -> std::convertible_to<std::size_t>;
};

这个hashable概念对许多用途都有意义。在这些情况下,t类型的对象上的哈希函数是专门化std::hash 。但是,出于我的目的,我不想假设哈希将是std::Hash 。我希望用户能够提供一个不同的哈希函数。

由于hashfunckey绑定得如此紧密,所以我不认为可以为hashfunckey定义单独的概念。那是正确的吗?因此,我想定义一个概念hashconcept,它同时处理hashfunckey

    null
template<typename HashFunc, typename Key>
concept Hash = requires(HashFunc h, Key k) {
    { std::invoke(h, k) } -> std::convertible_to<std::size_t>;
};
#include <functional>
#include <concepts>
#include <iostream>

template<typename HashFunc, typename Key>
concept HashConcept = requires(HashFunc h, Key k) {
    { std::invoke(h, k) } -> std::convertible_to<std::size_t>;
};


class HashFunc {
public:
    std::size_t operator()(int i) {
        return static_cast<size_t>(i);
    }
};

template<typename Hash, typename Key>
    requires HashConcept<Hash, Key>
size_t HashConceptUser(Hash h, Key k) {
    return h(k);
}

int main() {
    std::cout << HashConceptUser< HashFunc, int >(HashFunc{}, 3); 

}

共有1个答案

柯振濂
2023-03-14

这个列表看起来完整吗?

该列表可能缺少哈希函数最重要的一个条件:如果a==b,则h(a)==h(b)

列表中的第4个标准是好的哈希函数所需要的,它本身有些不完整--你不仅希望碰撞的可能性很小,还希望随机分散。hash函数h(i)=i满足第4个准则,但不是一个好的hash函数。另一方面,h(i)=0是一个糟糕的哈希函数,但应该被认为是有效的。

template <typename F, typename T>
concept HashFor = std::regular_invocable<F, T>
               && std::convertible_to<std::invoke_result_t<F, T>, size_t>;
template <typename F, typename T>
concept HashFor = std::regular_invocable<F, T>
    && requires(F f, T t) {
        { std::invoke(f, t) } -> std::convertible_to<size_t>;
    };
 类似资料:
  • 问题内容: 我需要一个可逆的哈希函数(显然,输入的大小将比输出小得多),该函数将输入以随机的方式映射到输出。基本上,我想要一种将“ 123”之类的数字转换为“ 9874362483910978”之类的较大数字的方法,但不是要保留比较的方法,因此,如果x1> x2,f(x1 )> f(x2)(但也不能始终为假)。 这种情况的用例是,我需要找到一种方法将小数字转换成看起来更大的随机数字。它们实际上并不

  • 我正在尝试编写一个C程序,使用哈希表来存储不同的单词,我需要一些帮助。 首先,我创建一个哈希表,其大小为最接近我必须存储的单词数的素数,然后我使用一个哈希函数为每个单词找到一个地址。我从最简单的函数开始,把字母加在一起,结果有88%的碰撞。然后我开始实验这个函数,发现无论我把它改成什么,碰撞都不会低于35%。现在我在用 这只是我想出来的一个随机函数,但它给了我最好的结果--大约35%的碰撞。 在过

  • 我需要一个尽可能有效的哈希函数,对于一个使用探测(开放寻址)进行冲突解决的哈希表(实际上是一个哈希集)。表中存储的条目都是4字节的INT,在该范围内具有随机值。 我正在考虑一些比djb2更快的东西,比如 然后用我的水桶尺寸再修改一次。我想这个素数一定比我的桶大小要大,这意味着我对我的表要增长多大也有某种理智上的限制(它可能永远不会超过256个条目)。 我不需要哈希函数的任何密码学方面--只要它不是

  • 主要内容:Hashtable 类中的属性,Hashtable 类中的方法在 C# 中,Hashtable(哈希表) 类表示根据键的哈希代码进行组织的键(key)/值(value)对的集合,可以使用键来访问集合中的元素。也就是说当您需要使用键来访问指定元素时,可以选择使用哈希表。 Hashtable 类中的属性 下表中列出了 Hashtable 类中一些常用的属性: 属性 描述 Count 获取哈希表中包含的键值对的个数 IsFixedSize 获取一个值,用来表示哈希

  • 主要内容:SHA-256哈希函数接受任意长度的输入字符串(数字,字母,媒体文件)并将其转换为固定长度。固定位长度可以变化(如32位或64位或128位或256位),具体取决于所使用的散列函数。固定长度输出称为散列。此哈希也是哈希算法的加密副产品。这如下所示。 哈希算法具有以下特性: 它产生一个唯一的输出(或哈希)。 它是一个单向的函数。 在像比特币这样的加密货币的情况中,区块链在其共识机制中使用这种加密哈希函数的属性。加密

  • 我正在我想要存储字符串的哈希程序中使用DJB2哈希函数。但是这个哈希函数返回一个非常大的无符号int值作为返回值(哈希表索引)。如果我的表大小很小(比如说13),有没有办法把这个大值转换成更小的。我只想尽可能避免碰撞。 DJB2哈希函数代码如下: