【发布时间】:2011-08-06 18:43:04
【问题描述】:
我编写了一个基本程序,它接受字符串并通过将它们插入到字符串->整数哈希映射中来计算唯一字符串的出现次数。
我使用 std::tr1::unordered_map 进行存储,为自定义哈希函数和自定义相等函数模板化。密钥类型实际上是char*,而不是太慢的std::string。
然后我更改了相同的代码以使用一个非常非常简单的哈希表(实际上是一个由哈希索引的 {key, value} 结构的数组),其大小为 2 的幂,并且对冲突进行线性探测。该程序的速度提高了 33%。
考虑到当我使用 tr1::unordered_map 时,我预先调整了哈希表的大小,因此它永远不必增长,并且我使用完全相同的哈希和比较例程,所以 tr1::unordered_map 这样做会减慢它的速度与可以想象的最基本的哈希图相比,增加了 50%?
我在这里所说的“简单”哈希映射类型的代码:
typedef struct dataitem {
char* item;
size_t count;
} dataitem_t;
dataitem_t hashtable[HASHTABLE_SIZE] = {{NULL,0}}; // Start off with empty table
void insert(char* item) {
size_t hash = generate_hash(item);
size_t firsthash = hash;
while (true) {
hash &= HASHTABLE_SIZE_MASK; // Bitmasking effect is hash %= HASHTABLE_SIZE
if (hashtable[hash].item == NULL) { // Free bucket
hashtable[hash].item = item;
hashtable[hash].count = 1;
break;
}
if (strcmp(hashtable[hash].item, item) == 0) { // Not hash collision; same item
hashtable[hash].count += 1;
break;
}
hash++; // Hash collision. Move to next bucket (linear probing)
if (hash == firsthash) {
// Table is full. This does not happen because the presizing is correct.
exit(1);
}
}
}
【问题讨论】:
-
什么是“本土”哈希图?
-
@Nawaz:我自己用大约 20 行 C 语言编写的。
-
@Borealid:所以如果你不发布你的代码,我们怎么能说为什么
std::tr1::unordered_map比你的“本土”哈希图慢? -
@Nawaz:我已经发布了代码。但是,就像我说的,它只是最简单的小哈希表。请记住,tr1::unordered_map 也已预先调整大小以适合数据。
-
分析器对测试时消耗的 CPU 时间有何看法?
标签: c++ hashmap unordered-map