C++:什么更快 - 在hashmap或switch语句中查找?

Has*_*tor 25 c++ performance hashmap switch-statement

我有一个代码模式,可以将一个整数转换为另一个整数.像这样:

int t(int value) {
    switch (value) {
        case 1: return const_1;
        case 3: return const_2;
        case 4: return const_3;
        case 8: return const_4;
        default: return 0;
    }
}
Run Code Online (Sandbox Code Playgroud)

目前它有大约50个条目,可能稍后会有更多,但可能不超过一百或两个.所有值都是预定义的,当然我可以按其值排序案例标签.所以问题是,什么会更快 - 这种方法或将其放入哈希映射(我无法访问std :: map,所以我说的是我的SDK中可用的自定义哈希映射)并在该表中执行查找?也许这有点过早优化,但是......但我只是需要你的意见.

提前致谢.

编辑:我的案例值将在0到0xffff的范围内.并且关于哈希映射的更好的可读性.我不知道是否真的会有更好的可读性,因为我还需要值来填充它,所以常量映射的是板材还是需要在我的代码的某个地方.

编辑2:已经给出了许多有用的答案,非常感谢.我想在这里添加一些信息.我的哈希键是整数,我的整数哈希函数基本上只是一个带有积分溢出的乘法:

EXPORT_C __NAKED__ unsigned int DefaultHash::Integer(const int& /*aInt*/)
{
_asm mov edx, [esp+4]
_asm mov eax, 9E3779B9h
_asm mul dword ptr [edx]
_asm ret
}
Run Code Online (Sandbox Code Playgroud)

所以应该很快.

peo*_*oro 24

switch构建体是更快的(或至少不慢).

这主要是因为switch构造将静态数据提供给编译器,而像哈希映射这样的运行时结构则不然.

可能的编译器应该将switch构造编译成代码指针数组:数组的每个项目(由索引索引)指向关联的代码.在运行时,这需要O(1),而哈希映射可能需要更多:平均情况下的O(log n)或最坏情况下的O(n),通常,并且无论如何更大的常量内存访问.

  • 我在教育中遇到了什么问题,我认为哈希应该是"O(1)",在最坏的情况下(许多碰撞)`O(N)`?我还要说开关的速度取决于你想要区分的值.如果它们是具有固定步长的闭合范围,则开关很快.但是像[1,100000000]那样随机输入的范围怎么样? (9认同)
  • O(n)中的哈希映射是一个非常糟糕的哈希映射 (3认同)

Sla*_*ava 6

我将加5美分:

对于大约50 std :: unordered_map(基于哈希,O(1))的条目数,通常比std :: map(基于树的O(ln(N)))要慢,并且两者都较慢,然后提升: :flat_map(排序向量O(ln(N))),在这种情况下,我倾向于使用。并非总是可以将switch编译为跳转表的情况,当是时,您可以简单地将自己的值(或函数)放入vector并按索引访问。否则,切换的速度比boost :: flat_map快一点。

如果您确实关心这段代码的性能,请在开头注意“通常”一词,进行性能分析(并与我们分享结果:)。


Jef*_*ter 5

Aswitch statement将比在哈希图中查找更快。

但是,如果您更改映射,映射将产生更具可读性的代码。您可以通过从文件中读取结果来轻松地使用地图来完成此操作。在 switch 语句中,您必须更改代码并重新编译。