我试图编写用于访问图像像素的优化代码,并且需要在不进入汇编级别的情况下使for循环超快.此外,沿着行进行索引以最小化高速缓存未命中.
这就是我所拥有的:
for (indr=0;indr<(height-1)*width;indr+=width) {
for (indc=0;indc<width;indc++){
I[indr+indc]= dostuff ;
}
}
Run Code Online (Sandbox Code Playgroud)
我不能使它成为一个循环,因为"dostuff"包括访问不在同一行上的元素.
有更快的方法吗?
编辑 好的,因为我之前的帖子稍微不清楚我在这里添加完整的代码.它非常难以理解,但一般的想法是我用一个简单的盒子使用积分图像进行卷积.图像首先在左侧和底部用ws + 1个零填充,在右侧和顶部用ws零填充.然后将其制成整体图像Ii.以下函数获取积分图像并提取卷积,其中结果Ic与原始图像的大小相同.
void convI(float *Ic,float *Ii,int ws, int width, int height)
{
int W=width+ws*2+1,indR;
int H=height+ws*2+1,indC;
int w=width, indr;
int h=height, indc;
int jmpA=W*(ws+1),jmpC=W*ws,jmpB=ws+1,jmpD=ws;
for (indR=W*(ws+1),indr=0;indr<width*(height-1);indR+=W,indr+=width) {
for (indC=ws+1,indc=0;indc<width;indC++,indc++){
//Performs I[indA]+I[indD]-I[indB]-I[indC];
Ic[indr+indc]=
Ii[indR-jmpA+indC-jmpB]+
Ii[indR+jmpC+indC+jmpD]-
Ii[indR+jmpC+indC-jmpB]-
Ii[indR-jmpA+indC+jmpD];
}
}
}
Run Code Online (Sandbox Code Playgroud)
这就是"dostuff"的一部分.循环缓慢.
如果您拥有所有优化级别,那么其他代码没有太多理由可以产生比您给出的更好的性能.
为什么你怀疑循环本身是一个瓶颈?如果不知道你在做什么,可以说不多.对您的代码进行基准测试,如果您有疑问,请查看它产生的汇编程序.
编辑:显示循环的内部部分后.
在循环之外尽可能多地放置索引计算的表达式有一点点潜力.由于它与循环变量混合在一起,因此可能无法对其进行优化.(或者只是重新排序索引的计算,以便编译器可以看到它并且可以尽可能地预先计算.)
最大的机会是性能困难来自您的载体的访问.如果您设法更好地计算索引,这也可能会改进,因为编译器/系统实际上会看到您以常规模式访问向量.
如果这没有帮助,请重新组织循环,使得向量的负载是增量的而不是存储.负载总是必须等到数据执行操作,存储不太明智.