编程珠玑:关于展开循环

关于展开循环对程序性能的影响

昨天看到了CSAPP上优化程序性能一章,印象最深的一点是关于展开循环的描述。关于展开循环,上面是这样描述的:
**展开循环是一种程序变换,通过增加每次迭代计算的元素的数量,减少循环的迭代次数。**

循环展开能从两方面改进程序的性能。

  • 减少了不直接有助于程序结果的操作的数量,例如循环索引计算和分支条件。
  • 提供了一些方法,可以进一步变化代码,减少整个计算中关键路径上的操作数量。

下面是一个将一个int 类型数组初始化为0的代码段:

void Init_Array(int *dest, int n)
{
    int i;
    for(i = 0; i < n; i++)
        dest[i] = 0;
}

而如果用循环展开的话,代码如下:

void Init_Array(int *dest, int n)
{
    int i;
    int limit = n - 3;
    for(i = 0; i < limit; i+= 4)//每次迭代处理4个元素
    {
        dest[i] = 0;
        dest[i + 1] = 0;
        dest[i + 2] = 0;
        dest[i + 3] = 0;
    }
    for(; i < n; i++)//将剩余未处理的元素再依次初始化
        dest[i] = 0;
}

将循环展开后,每次迭代将初始化4个元素,因为元素的数量不一定输4的整数倍,所以在每次处理4个元素后还要讲剩下的元素再进行初始化。

当然这里的 int limit = n - k(本例中k = 3) 中的k是根据要处理元素的个数来自己确定的。具体怎么选择这里不作描述。通常循环展开是提高程序性能的可靠方法。

根据描述给出书中优化程序性能的基本策略:

  1. 高级设计。为遇到的问题选择适当的算法和数据结构。要特别警觉,避免使用那些会渐进产生糟糕性能的算法和编码技术。
  2. 基本编码原则。避免限制优化的因素,这样编译器就能产生高效的代码。

    1)消除连续的函数调用。在可能时,将计算移到循环外。考虑有选择性的妥协程序的模块性已获得更大的效率。
    2)消除不必要的存储器引用。引入临时变量来保存中间结果。只有在最后的值计算出来时,才将结果放到数组或全局变量中。

  3. 低级优化
    1)展开循环,降低开销,并且使得进一步的优化成为可能。
    2)通过使用例如累积变量和重新结合等技术,找到方法提高指令级并行。
    3)使用功能的风格重写条件操作,使得编译采用条件数据传送。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值