我正在尝试使用4向循环展开来优化此c代码

我正在尝试做的是使用这个C代码并使用一种称为循环展开的技术对其进行优化,但在这种情况下,我想使用四向循环展开。 现在,我理解了这项技术,并且我理解了我不知道如何将其应用于此代码的概念。 我是否需要添加一些额外的变量? 在每个循环之后还是在所有循环结束时,我是否必须有一些代码? 此代码是8×8块代码,用于处理像素并以逆时针方向旋转90度。 任何帮助将不胜感激。 谢谢。

/* * rotate8 - rotate with 8x8 blocking */ char rotate8_descr[] = "rotate8: rotate with 8x8 blocking"; void rotate8(int dim, pixel *src, pixel *dst) { int i, j, ii, jj; for(ii = 0; ii < dim; ii += 8) for(jj = 0; jj < dim; jj += 8) for (i = ii; i < ii + 8; i++) for (j = jj; j < jj + 8; j++) dst[RIDX(dim-1-j, i, dim)] = src[RIDX(i, j, dim)]; } 

您可以使用8行显式代码替换内部循环

  dst[RIDX(dim-1-jj, i, dim)] = src[RIDX(i, jj, dim)]; dst[RIDX(dim-1-(jj+1), i, dim)] = src[RIDX(i, (jj+1), dim)]; ... dst[RIDX(dim-1-(jj+7), i, dim)] = src[RIDX(i, (jj+7), dim)]; 

所以你要通过为每个值显式写一行代替循环变量。

现在你可以重复下一个循环的8个值,​​你将有8 x 8行代码,依此类推。

除了理解练习之外的任何事情,这对我来说似乎毫无意义,编译器非常有效地完成这类工作,他们会在有意义的地方进行优化。 手动滚动很少产生最佳代码。

我想说一下它 – 然后我自己这样做了。 令人惊讶的是 – 内部循环在您的布局中执行速度最快 – 手动展开它实际上更慢。

然而 – 真正的问题是RIDX宏。 切换内存布局和切换外环会产生重大影响。

这是我最快的缩进版本,以显示它与您的版本的不同之处。 假定RIDX宏是定义的。

 #define RIDX(x,y,d) (x+(y)*(d)) typedef unsigned char pixel; void rotate8(int dim, pixel *src, pixel *dst) { int i, j, ii, jj; for(jj = 0; jj < dim; jj += 8) for(ii = 0; ii < dim; ii += 8) for (i = ii; i < ii + 8; i++) for (j = jj; j < jj + 8; j++) dst[RIDX(dim-1-j, i, dim)] = src[RIDX(i, j, dim)]; } 

...经验教训:总是概况:-)

 gcc -funrull-loops

你不应该自己展开循环,除非GCC不能这样做(查看程序集)并且你已经通过使用分析器certificate你必须加速这部分代码。

您拥有的示例代码看起来像是自动循环展开的完美候选者。

其他一些有用的标志:

 -O3 //开启了很多优化(几乎所有)
 -ftree-vectorize -msse2 //自动向量化一些循环

http://www.relisoft.com/book/lang/pointer/2ptrarr.html

如果您的编译器无法优化算法的人类可读,可维护版本,并且您必须兼作人工编译器 – 购买新的编译器! 没人能买得起人类编制者了。 所以,请怜悯自己和那些必须查看代码的程序员。