2017-04-16 1213 views
3

我有一个算法的两个C++实现,称它们为ABAB之间唯一的区别是A使用std::unordered_map<int, int> hashmap;,但B使用google::dense_hash_map<int, int> hashmap;什么是__memset_sse2,它为什么执行如此多的指令?

我发现一个输入,其中AB慢得多,我不明白为什么。

对于相同的输入,我跑sudo perf record -e instructions ./A input.txt

,然后我得到这样的结果:

Overhead Command Shared Object  Symbol 
    65.90% A  libc-2.23.so   [.] __memset_sse2 
    6.63% A  libc-2.23.so   [.] _int_malloc 
    3.44% A  libc-2.23.so   [.] malloc 
    2.61% A  libc-2.23.so   [.] _int_free 

当我为B这是做同样的快,我得到如下:

Overhead Command Shared Object  Symbol 
    15.17% B  libc-2.23.so   [.] _int_malloc 
    14.94% B  B     [.] B::func1() 
    5.72% B  B     [.] B::func2() 
    5.58% B  B     [.] B::func3() 

什么是__memset_sse2以及它为什么执行如此多的指令?

+0

'__memset_sse2'只是SSE2优化的[memset]版本(http://en.cppreference.com/w/cpp/string/byte/memset)。尝试使用'-g'运行'perf'并检查输出中的调用图 – myaut

回答

4

__memset_sse2用于implementationsmemset功能针对支持SSE2的体系结构进行了优化。当你看到它占用了大约三分之二的执行时间时,这意味着大部分时间都用来初始化一个内存块,它有一个相对较大的大小。散列表很可能使用memset来初始化其散列桶。

看起来google::dense_hash_map针对大小进行了优化,因此在运行示例时不需要初始化更多的内存。

注意:观察到初始化占用CPU时间的三分之二可能意味着您的基准测试的设计不正确。也许您通过哈希容器放入的数据量相对较少,或者您在每次运行时都要重新构建容器。