将并行执行策略与 std::back_inserter 一起使用是不是安全?

Posted

技术标签:

【中文标题】将并行执行策略与 std::back_inserter 一起使用是不是安全?【英文标题】:Is it safe to use parallel execution policies with std::back_inserter?将并行执行策略与 std::back_inserter 一起使用是否安全? 【发布时间】:2021-02-08 12:21:00 【问题描述】:

我想知道当输出为std::back_insert_iterator 时使用执行策略std::execution::parstd::execution::par_unseq 是否安全。例如:

std::vector<std::string> src(100, "test"), dst;
std::move(std::execution::par_unseq, src.begin(), src.end(), std::back_inserter(dst));

是否保证不会对目标向量进行并发插入?

【问题讨论】:

当使用并行执行策略时,程序员有责任避免数据竞争和死锁 taken from. 这并不安全,正如您对 STL 容器所期望的那样。 算法不知道迭代器将元素插入容器的事实。从算法的观点来看,它只是一个允许访问元素的迭代器。 &lt;algorithm&gt; 中的并行算法需要前向迭代器,std::back_insert_iterator 不是。所以这不仅仅是不安全的。这是完全禁止的。 【参考方案1】:

std::vector 上调用push_back 不符合par_unseqpar 的要求。

所以不,这不安全。

通过说par,您承诺对用于输入和输出的迭代器的访问不包含竞争条件。在这里失败了。

par_unseq 需要您更多的承诺;基本上,你们都没有数据竞争,并且你们的算法适合矢量化(批量处理)。

push_back 不符合条件,back_inserter 是根据push_back 定义的。

另一方面:

std::vector<std::string> src(100, "test"), dst(100, "");
std::move(std::execution::par_unseq, src.begin(), src.end(), dst.begin());

这是有效的,因为您可以并行和同时访问 vector 的各个元素(vector&lt;bool&gt; 除外)

【讨论】:

以上是关于将并行执行策略与 std::back_inserter 一起使用是不是安全?的主要内容,如果未能解决你的问题,请参考以下文章

垃圾收集器与内存分配策略之垃圾收集器

(转)OLAP 任务的并发执行与调度

JDK并发策略

Quartz定时任务的并行与串行

将多个并行功能发布到同一应用程序中的 Git 分支策略

API 管理高级策略 - 将并发限制为 1