0

我正在寻找一个实用的循环展开技术示例。

我认为达​​夫的设备是一个不错的提示。
但是Duff 的设备的目的地永远不会增加。它可能对将数据复制到串行设备的嵌入式程序员有用,而不是一般程序员。

你能给我一个很好的有用的例子吗?
如果你曾经在你的真实代码中使用过它,它会更好。

4

3 回答 3

4

最实用的技术是学习并喜欢编译器的优化选项,如果在分析中遇到热点,偶尔手动检查生成的程序集。

于 2011-04-03T01:33:39.147 回答
1

我不确定您所说的“目的地永远不会增加”是什么意思。

手动循环展开是相当少见的。今天的嵌入式微处理器已经足够快了,这样的优化是不必要的(并且会浪费宝贵的程序内存)。

我在线性求解器内核中使用了 Duff 设备的变体。back_step每个必须有一个fwd_step,并且以四人一组的形式进行。

请注意,前向和后向循环由gotos 实现。当跳过ifin时fwd_step,执行跳转到后向循环的中间。所以它真的是一种双达夫装置。

这不是任何一种“实用”技术,它只是我能找到的表达一些非常复杂的流控制的最佳方式。

switch ( entry ) {

#define fwd_step( index )                                                                                         \
                                                                                                     \
case (index):                                                                                                    \
    if ( -- count ) {                                                                                               \
        ...

startf:
    fwd_step( 0 )
    fwd_step( 1 )
    fwd_step( 2 )
    fwd_step( 3 )

        stream = stream_back;
        goto startf;


#define back_step( index )                                                            \
        .... \
    }                                                                                    \

startb:
    stream -= block_size;

    back_step( 3 )
    if ( ! -- countb ) break;
    back_step( 2 )
    if ( ! -- countb ) break;
    back_step( 1 )
    if ( ! -- countb ) break;
    back_step( 0 )
        if ( -- countb ) goto startb;
} // end switch
于 2011-04-03T01:43:58.313 回答
0

(为了其他人的利益,可以在此处此处找到 Duff 设备的背景)

我在图像处理优化中遇到过它,特别是在处理要复制的像素少于完整平铺或内核的边界条件时(这可以避免在每个坐标处进行测试。)

于 2011-04-03T01:42:18.610 回答