我有一个算法可以对数组元素进行一些计算。我想重新使用输入数据缓冲区将结果写入其中。 就数据遍历模式而言,它看起来几乎与此完全相同(for循环中发生的唯一其他事情是某些指针和计数变量的增量):
int *inputData = /*input data is here */;
for(int i=0;i<some_value;++i)
{
int result = do_some_computations(*inputData);
*inputData = result;
++inputData;
}
现在有趣的部分:inputData包含大约六百万个元素。如果我注释掉对inputData数组的写入,那么算法看起来基本上是这样的:
int *inputData = /*input data is here */;
for(int i=0;i<some_value;++i)
{
int result = do_some_computations(*inputData);
// *inputData = result;
++inputData;
}
该算法在一系列约100次测量中平均需要大约7毫秒。但是,如果我保留写入,算法大约需要55毫秒。写“* inputData = do_some_computations(* inputData);”而不是它现在的方式在性能上没有区别。使用单独的outputBuffer也没有区别。
这很糟糕。该算法的性能对程序的要求绝对至关重要。我对7ms非常满意,但是我对55毫秒非常不满意。
为什么这次单次回写会导致如此大的开销,我该如何解决?
答案 0 :(得分:4)
您的代码在非写回版本中被优化为零。为了表明这一点,假设一个5GHz的单核CPU,那么: -
7ms = 35,000,000次循环
600万件= 35/6 =每件5.8个周期=没有做很多工作
慢速版: -
55ms = 275,000,000次循环
600万件= 275/6 =每件45.8个周期=每个项目的工作量更多
如果要验证这一点,请查看编译器的汇编输出。