unordered_map - 哈希函数不起作用
unordered_map - Hash function has no effect
为什么在下面的哈希函数(返回常量 0)似乎没有任何效果?
由于哈希函数返回常量,我期望输出所有值均为 3。但是,它似乎唯一地将std::vector
值映射到唯一值,而不管我的哈希函数是否恒定。
#include <iostream>
#include <map>
#include <unordered_map>
#include <vector>
// Hash returning always zero.
class TVectorHash {
public:
std::size_t operator()(const std::vector<int> &p) const {
return 0;
}
};
int main ()
{
std::unordered_map<std::vector<int> ,int, TVectorHash> table;
std::vector<int> value1({0,1});
std::vector<int> value2({1,0});
std::vector<int> value3({1,1});
table[value1]=1;
table[value2]=2;
table[value3]=3;
std::cout << "n1=" << table[value1];
std::cout << "n2=" << table[value2];
std::cout << "n3=" << table[value3];
return 0;
}
获得的输出:
1=1
2=2
3=3
预期产出:
1=3
2=3
3=3
关于哈希,我错过了什么?
你误解了哈希函数的使用:它不用于比较元素。在内部,映射将元素组织到存储桶中,哈希函数用于确定元素所在的存储桶。元素的比较是用另一个模板参数执行的,看看unordered_map
模板的完整声明:
template<
class Key,
class T,
class Hash = std::hash<Key>,
class KeyEqual = std::equal_to<Key>,
class Allocator = std::allocator< std::pair<const Key, T> >
> class unordered_map;
哈希器之后的下一个模板参数是密钥比较器。要获得预期的行为,您必须执行以下操作:
class TVectorEquals {
public:
bool operator()(const std::vector<int>& lhs, const std::vector<int>& rhs) const {
return true;
}
};
std::unordered_map<std::vector<int> ,int, TVectorHash, TVectorEquals> table;
现在,您的地图将具有单个元素,并且所有结果都将3
。
一个健全的哈希表实现不应该丢失信息,即使存在哈希冲突。有几种技术可以解决冲突(通常在运行时性能与数据完整性之间进行权衡)。显然,std::unordered_map
实现了它。
请参阅: 哈希冲突解决方案
添加一个谓词键比较器类。
class TComparer {
public:
bool operator()(const std::vector<int> &a, const std::vector<int> &b) const {
return true; // this means that all keys are considered equal
}
};
像这样使用它:
std::unordered_map<std::vector<int> ,int, TVectorHash, TComparer> table;
然后,其余代码将按预期工作。
相关文章:
- 仅包含可移动 std::map 的类的移动构造函数不起作用
- 为什么我的数组双精度函数不起作用?
- std::函数不起作用,但普通的旧函数指针可以 - 为什么?
- C++ Arduino - 随机函数不起作用
- 为什么我的数组或函数不起作用?
- 从类中的另一个文件请求函数不起作用
- 双链表堆栈删除函数不起作用
- 将 cmake 代码段转换为函数 - 不起作用
- 为什么我的从base64解码的函数不起作用?
- 为什么当我们使用等于'='符号比较器函数时,c ++的内置排序函数不起作用?
- swap(int&, int&) 函数不起作用,当交换不使用临时变量时?
- 子类化 STL 容器:范围构造函数不起作用
- 带有此指针的模板类多重继承构造函数不起作用?
- 以下打印树函数不起作用为什么?
- 为什么内存集函数不起作用?
- 调用填充我的主体数组的函数不起作用
- 带有自定义数字的阶乘函数不起作用
- 如何QDialog raise()函数不起作用
- Lambda 表达式闭包函数不起作用
- C++:在没有 lvalue 的情况下调用时复制构造函数不起作用