【问题标题】:C++ Parallel Loop without locking critical section using PPL使用 PPL 不锁定关键部分的 C++ 并行循环
【发布时间】:2013-02-16 09:59:55
【问题描述】:

在下面的代码中,有使用 PPL 实现的 parallel_for 循环。主要问题在这里;当我被注释 cs.lock() 和 cs.unlock() 时,abc 向量值不正确。我正在使用 concurrency_vector 类型来随机访问数组值,但它似乎不起作用。锁定关键部分,它工作但很慢。此外,为了加快速度,我使用索引来存储值,而不是使用 2D-concurrency_vector。问题是什么,没有锁定关键部分,我错过了什么?

#include <iostream>
#include <ppl.h>

using namespace concurrency;
using namespace std;

int test_function()
{
    critical_section cs;

    concurrent_vector< double > abc( 300 * 400, 1000 );

    parallel_for ( 0, 1000, [ & ]( int k ) {
        for ( int y = 0; y < 300; y++ ) {
            for ( int x = 0; x < 400; x++ ) {

                /// k is using with some calculations for thr

                cs.lock();

                if ( thr < abc[ 400 * y + x ] ) {

                    abc[ 400 * y + x ] = thr;
                }

                cs.unlock();
            }
        }
    } );
}

【问题讨论】:

    标签: c++ parallel-processing ppl parallel-for


    【解决方案1】:

    您为什么希望它起作用?如果它在没有锁定的情况下并行运行,abc[400*y+x] 可以并且将在 if 语句和赋值之间进行更改,从而破坏您的逻辑。向量类型本身是线程安全的与此无关。

    【讨论】:

    • 感谢您的快速回答,我是否正确,if 语句导致了问题,我们应该保护它?
    • @user2055437 似乎是这样,除非您的计算中有其他可能破坏它的东西。当然这会很慢——锁定/解锁很慢,你需要做很多事情。你最终也会有很多不必要的等待。如果您改用粒度锁(创建 300*400 临界区,为 abc 的每个元素一个,然后使用它们进行锁定),您可能会看到一些性能改进。
    • 很抱歉占用了您的时间,您能否提供一些代码块示例或示例网站,我可以阅读的书,您说加快速度?
    • @user2055437 它可能加速它(实际上它可能会)。我很想在聊天中这样做,不幸的是你需要 20 代表才能在那里交谈。基本上,而不是critical_section cs; critical_section css[300*400] 而不是cs.lock() / cs.unlock() cs[400*y+x].lock()/cs[400*y+x].unlock()。我不确定创建和保存关键部分的成本有多大,所以我不确定这是否有帮助,但如果它们像我认为的那样便宜,那么这应该会有所改善。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-12-22
    • 1970-01-01
    • 1970-01-01
    • 2019-01-15
    • 2010-11-03
    相关资源
    最近更新 更多