1

我有一个关于减少循环中的内存调用数量的问题。考虑下面的代码(这不是我的代码,因为它太长了,我不能在这里表示它):

for(k=0;k<n;k++)
{
    y[k] = x[0]*2 + z[1];
}

如您所见,在每次迭代中,内存中的相同块 (x[0], z[1]) 都被调用。我想知道当同一个内存块被多次调用时,是否有任何方法可以减少内存访问。提前致谢。

4

5 回答 5

6

简单地说,在循环之前获取值:

i = x[0];
j = z[1];
for(k=0;k<n;k++)
{
    y[k] = i*2 + j;
}

当然,即使您不进行任何更改,编译器也会对此进行优化(如果可以的话),但这有助于编写更具可读性和直观性的代码。您不需要在每次迭代中获取值,您编写的代码应该表明这一点。
忘记微优化编写更直观和可读的代码!

正如评论中正确指出的那样,右手表达式完全独立于循环,因此:

i = x[0]*2 + z[1];
for(k=0;k<n;k++)
{
    y[k] = i;
}
于 2013-01-28T05:52:13.067 回答
2

这是你可以做的。

float value =  x[0]*2 + z[1];

for(k=0;k<n;k++)
{
  y[k] = value;
}

希望这可以帮助。

于 2013-01-28T05:58:39.770 回答
1
v = x[0]*2 + z[1];
for(k=0;k<n;++k) y[k] = v

假设 x[0] 和 z[1] 没有映射到 y[0..n-1]

于 2013-01-28T05:59:14.670 回答
1

如果z类型比int(例如char)短,您可以尝试以下技巧:

char value = x[0]*2 + z[1];
unsigned int value32 = value | (value << 8) | (value << 16) | (value << 24);

unsigned int k;

// Going by blocks of 4
for(k = 0; k < n - n%4; k+=4) {
    (unsigned int)z[k] = value32;
}

// Finishing loop
for(; k < n; k++) {
    z[k] = value;
}
于 2013-01-28T06:53:55.983 回答
0

编译器会对此进行优化,

但是,如果您使用没有优化的损坏编译器:您可以将它们都放在register整数中,然后使用它们。像这样:

x0 = x[0]*2;
z1 = z[1];
y0 = x0 + z1;
register int k;
for(k=0;k<n;k++)
{
   y[k] = y0;
}

这并不能保证 x[0] 和 z[1] 将在一个寄存器上,但至少提示编译器它们应该在一个寄存器上。

于 2013-01-28T05:55:28.483 回答