在发生L3缓存未命中之前,向量中可迭代的对象数量是多少?

时间:2014-05-19 19:06:49

标签: c++ performance cpu shared-ptr cpu-architecture

假设我有一个包含堆分配内存的数据成员的类:

class X{
    std::map<int, double> a;
    std::set<int> b;
    std::vector<int>;
    std::string c;
}

我有一个std::vector<shared_ptr<X>>包含许多这些X个对象,我将遍历并访问map.begin():

for(int i =0; i<vec.size(); i++){
    running_total += *(vec[i]->a.begin());
}

理论上,在遇到L3缓存未命中之前,我应该能够在向量中保存/迭代多少个对象?

我认为答案是L3缓存可容纳的每个对象有多少缓存行,但L3 size / sizeof(x_element.get())似乎没有给出我从分析中看到的答案....

我的L3缓存是8MB,每个缓存行是64字节,因此在L3缓存未命中之前我可以容纳大约125,000个对象。但是我看到L3缓存未命中的矢量元素数量要少得多。

1 个答案:

答案 0 :(得分:1)

在Intel CPU上,您可以使用Intel Architecture Code Analyzer (IACA)来分析循环。如果我没记错的话,如果你正确配置它也可以分析缓存未命中等等。

另一个工具是Valgrind,它是一个模拟器,如果你正确配置它也可以用来模拟缓存行为。

但总的来说 - 为了最大化缓存使用率 - 您应该将在一个线性数组中迭代的数据分开(并尽可能小)。例如。一个数组包含键(或迭代的数据)和一个数组,其余如果可能。因此,简而言之,只有当您迭代的数据的地址是线性排序而不是随机访问时,如果迭代堆上不同位置分配的许多对象,缓存才会真正启动。