0

我正在编写一些代码,并试图尽可能地优化它,基本上让它在一定的时间限制下运行。

以下是调用...

static affinity_partitioner ap;
parallel_for(blocked_range<size_t>(0, T), LoopBody(score), ap);

...以下是执行的内容。

void operator()(const blocked_range<size_t> &r) const {

    int temp;
    int i;
    int j;
    size_t k;
    size_t begin = r.begin();
    size_t end = r.end();

    for(k = begin; k != end; ++k) { // for each trainee
        temp = 0;
        for(i = 0; i < N; ++i) { // for each sample
            int trr = trRating[k][i];
            int ei = E[i];              
            for(j = 0; j < ei; ++j) { // for each expert
                temp += delta(i, trr, exRating[j][i]);
            }
        }           
        myscore[k] = temp;
    }
}

我正在使用英特尔的 TBB 来优化它。但我也一直在阅读有关 SIMD 和 SSE2 以及类似性质的内容。所以我的问题是,如何将变量 (i,j,k) 存储在寄存器中,以便 CPU 可以更快地访问它们?我认为答案与实施 SSE2 或它的一些变体有关,但我不知道如何做到这一点。有任何想法吗?

编辑:这将在 Linux 机器上运行,但我相信使用英特尔的编译器。如果有帮助,我必须在执行任何操作以确保编译器工作之前运行以下命令... source /opt/intel/Compiler/11.1/064/bin/intel64/iccvars_intel64.csh; source /opt/intel/tbb/2.2/bin/intel64/tbbvars.csh ...然后编译我做: icc -ltbb test.cxx -o test

如果没有简单的方法来实现 SSE2,关于如何进一步优化代码的任何建议?

谢谢, 赫里斯托

4

4 回答 4

1

当你想在 C++ 模块中使用汇编语言时,你可以把它放在一个asm块中,然后继续在块外使用你的变量名。您在块中使用的汇编指令asm将指定正在操作的寄存器等,但它们会因平台而异。

于 2010-04-29T16:59:01.127 回答
1

您的问题代表了对正在发生的事情的一些困惑。i,j,k 变量几乎肯定已经保存在寄存器中,假设您正在编译优化(您应该这样做 - 在您的 icc 调用中添加“-O2”)。

您可以使用asm块,但考虑到您已经在使用 ICC,更简单的方法是使用 SSE 内在函数。英特尔为他们提供的文档在这里 - http://www.intel.com/software/products/compilers/clin/docs/ug_cpp/comm1019.htm

看起来您可以对顶级循环进行 SIMD 化,尽管这在很大程度上取决于您的delta功能是什么。

于 2010-04-29T17:08:50.153 回答
0

如果您使用 GCC,请参阅http://gcc.gnu.org/projects/tree-ssa/vectorization.html了解如何帮助编译器自动矢量化您的代码和示例。

否则,您需要让我们知道您使用的是什么平台。

于 2010-04-29T16:56:56.353 回答
0

编译器应该为您执行此操作。例如,在 VC++ 中,您可以简单地打开 SSE2。

于 2010-04-29T17:42:49.890 回答