gpt4 book ai didi

c++ - std::hash 特化仍未被 std::unordered_map 使用

转载 作者:行者123 更新时间:2023-11-30 01:14:29 25 4
gpt4 key购买 nike

我正在尝试扩展 std::hash<T>通过为 const char 提供特化, 这样我就可以使用 const char*作为 std::unordered_map 中的键类型.

这是我尝试过的:

#include <unordered_map>
#include <functional>
#include <stdio.h>
#include <string.h>
#include <ctype.h>

namespace std
{
template<>
struct hash<const char*>
{
size_t operator()(const char* const& s) const
{
size_t h = 0;
const char* tmp = s;

while (*tmp)
h = (h << 5) + h + (unsigned char)toupper(*tmp++);

printf("hash of '%s' is (%ld)\n", s, h);
return h;
}
};
}

int main(int argc, char* argv[])
{
const char* name1= "Mark Nelson";
const char* name2= strdup(name1);

std::unordered_map<const char*, int> map;

printf("Insert (%s)\n", name1);
map[name1]= 100;

printf("Lookup (%s)\n", name1);
printf("map[%s](name1) = %d\n", name1, map.find(name1) != map.end() ? map.find(name1)->second : -1);
printf("Lookup (%s)\n", name2);
printf("map[%s](name2) = %d\n", name2, map.find(name2) != map.end() ? map.find(name2)->second : -1);

return 0;
}

输出是什么:

Insert (Mark Nelson)
hash of 'Mark Nelson' is (121066894705597050)
Lookup (Mark Nelson)
hash of 'Mark Nelson' is (121066894705597050)
hash of 'Mark Nelson' is (121066894705597050)
map[Mark Nelson](name1) = 100
Lookup (Mark Nelson)
hash of 'Mark Nelson' is (121066894705597050)
map[Mark Nelson](name2) = -1

所以对我来说,std::unordered_map正在使用我提供的哈希实现来进行插入和查找。但由于某种原因,它没有通过 name2 找到值,它似乎仍然使用指针比较。

这里有什么问题?我使用的是 GCC 4.8.2,文件是用 g++ -std=c++11 main.cc 编译的

最佳答案

无序 map ( ref ) 需要两件事:

  1. 哈希函数
  2. 相等比较函数

所以您有 (1),它似乎可以工作,但随后 map 必须检查 const char * 是否相等,这会转化为指针比较。为此,您可以指定一个自定义比较器 ( ref ):

struct cmp_str
{
bool operator()(char const *a, char const *b)
{
return std::strcmp(a, b) == 0;
}
};

std::unordered_map<const char*, int, std::hash<const char *>, cmp_str> BlahBlah;

关于c++ - std::hash 特化仍未被 std::unordered_map 使用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30101477/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com