我正在运行一个简单的二维数组读写访问基准测试练习.
我有const int XDim = 1000;
和const int YDim = 1000;
,并创建了一个1000 x 1000
矩阵.
在C风格中,我使用
double* doubleArray[XDim];
for (int i = 0; i < XDim; i++)
doubleArray[i] = (double*)malloc(YDim * sizeof(double));
for (int i = 0; i < XDim; i++)
for (int j = 0; j < YDim; j++)
doubleArray[i][j] = 0.;
在C++std::vector<std::vector<double>>
中,我使用:
std::vector<std::vector<double>> doubleArray;
std::vector<double> vecdbl;
for (int i = 0; i < XDim; i++)
doubleArray.push_back(vecdbl);
for (int i = 0; i < XDim; i++)
for (int j = 0; j < YDim; j++)
doubleArray[i].push_back(0.);
在Boost风格中,我使用:
typedef boost::multi_array<double, 2> OuterArray;
typedef boost::array<OuterArray::index, 2> OuterArrayIndices;
OuterArray::index rows = XDim;
OuterArray::index cols = YDim;
OuterArrayIndices shape = { rows, cols };
OuterArray doubleArray(shape);
for (int i = 0; i < XDim; i++)
for (int j = 0; j < YDim; j++)
doubleArray[i][j] = 0.;
然后,我从doubleArray[][]
中随机 Select 999999
个元素,并将它们设置为[-5, 5]
中 Select 的随机整数值.然后,我进一步随机挑选999999
个元素,将它们相加,然后求出它们的平均值.找到平均值,并显示所有这些操作所用的时间.这个练习重复了很多次.
完成这一切的Godbolt链接有here多个
在上面的链接中,龙箭似乎只处理了const int total_iterations = 2;
个.较大的值表示已超过时间的错误.在我的带有const int total_iterations = 100;
的计算机上运行它时,我观察到一个一致的模式,即Boost方法无法匹配malloc
的C方法或std::vector<std::vector<double>>
的C++方法.在后两者之间,大多数情况下,C方法优于C++方法,但也有一些相反的实例.所有这些都是在使用默认设置的发布模式下在Visual Studio中编译和运行的.
相对于指针或std::vector<std::vector<double>>
的原始C指针,我看不到boost::multi_array
的值.有没有方法可以更快地制造boost::multi_array
?
102:根据 comments 、对数组元素的顺序访问以及在Godbolt上的发布模式设置,boost::multi_array
在大多数情况下获胜.看10次中的here次9次.
由于对元素的非连续、随机访问,以及在Godbolt上的发布模式设置,它很接近,C风格略好于boost::multi_array
.见here
多亏了tstanisl的 comments ,对于顺序访问,C风格似乎要快10倍.他的链接可访问here
用户n-m-can-be-an-ai指出了一个总体警告,即此剖析可能正在剖析随机数生成器.控制这一点似乎超出了这个问题的范围.然而,似乎无论如何,由于为每种情况生成相同数量的RNG,并且迭代次数也不是1或2,而是更大,这可能是一次洗牌.我可能错了.
101(2):根据chqrlie提供的答案,我修改了可用的代码here.我已经对它进行了充分的 comments ,希望能看到正在发生的事情.我仍然不完全清楚哪种方法更快,但也许其他人可以使用这段代码作为起点,更好地对这些不同的数据 struct 进行基准测试.