命名空间
变体
操作

std::execution::bulk, std::execution::bulk_chunked, std::execution::bulk_unchunked

来自 cppreference.cn
< cpp‎ | execution
 
 
 
定义于头文件 <execution>
std::execution::sender

auto bulk( std::execution::sender auto input,
           std::integral auto size,
           auto&& policy,
           std::invocable<decltype(size),

                          /*values-sent-by*/(input)...> function );
(1) (自 C++26 起)
std::execution::sender

auto bulk_chunked( std::execution::sender auto input,
                   std::integral auto size,
                   auto&& policy,
                   std::invocable<decltype(size), decltype(size),

                                  /*values-sent-by*/(input)...> function2 );
(2) (自 C++26 起)
std::execution::sender

auto bulk_unchunked( std::execution::sender auto input,
                     std::integral auto size,
                     std::invocable<decltype(size), decltype(size),

                                    /*values-sent-by*/(input)...> function );
(3) (自 C++26 起)

目录

[编辑] 参数

input - 发送器,一旦执行,会发送函数执行所依据的值
policy - 附加到 function/function2执行策略
function - 可调用对象,将为范围 [0size) 中的每个索引调用,同时也会传递输入发送器生成的值
function2 - function 相同,但使用索引对 (be) 调用,其中 b < e,因此,对于范围 [[0size) 中的每个索引 i,都恰好调用一次 function2,使得 b <= i < e

[编辑] 返回值

返回一个发送器,描述由输入发送器描述的任务图,并添加一个节点,该节点使用范围 [0size) 中的索引调用提供的函数,同时也将输入发送器发送的值作为参数传递。

function/function2 保证在返回的发送器启动之前不会开始执行。

[编辑] 错误完成

所有由 input 传入的错误都会被转发。

此外,允许发送器以包含 std::exception_ptr 错误的错误完成:

  • function 抛出的任何异常
  • 如果实现无法分配所需资源,则为 std::bad_alloc
  • 对于其他内部错误(例如,无法将异常从执行上下文传播到调用者)的从 std::runtime_error 派生的异常。

[编辑] 取消

未定制的 std::execution::bulkstd::execution::bulk_chunkstd::execution::bulk_unchunked 会转发来自 input 的停止完成信号。它们不提供产生停止完成信号的额外机制。

[编辑] 注解

当调用 std::execution::bulkstd::execution::bulk_chunked 时,function/function2 的不同调用可能发生在同一执行代理上。

当调用 std::execution::bulk_unchunked 时,function 的不同调用必须发生在不同的执行代理上。

std::execution::bulk 的默认实现基于 std::execution::bulk_chunked。虽然可以自定义 std::execution::bulk,但预计大多数情况下只会自定义 std::execution::bulk_chunked

在没有自定义 std::execution::bulkstd::execution::bulk_chunked 的情况下,std::execution::bulkstd::execution::bulk_chunk 的行为是串行执行 function,这并不是特别有用。 期望实现具有自定义项,这将使在不同调度器上运行 std::execution::bulkstd::execution::bulk_chunked 更有用。

std::execution::bulk_unchunked 旨在用于 function 的不同调用之间可能存在依赖关系,并且需要并发前向进度保证(并行前向进度是不够的)的情况。 使用大小为 1000 运行 std::execution::bulk_unchunked 将需要 1000 个执行代理(例如,线程)同时运行。

std::execution::bulk_unchunked 不需要执行策略,因为已经预期 function 能够并发运行。

[编辑] 示例

execution::bulk 的可能用法。

std::vector<double> x;
std::vector<double> y;
//...
sender auto process_elements
    = just(get_coefficient())
    | bulk(x.size(), [&](size_t i, double a)
    {
        y[i] = a * x[i] + y[i];
    });
// process_elements describes the work described by calling a function to
// get a coefficient `a`, and using it to execute
//   y[i] = a * x[i] + y[i]
// for each `i` in range [0, x.size())

execution::bulk_chunked 的可能用法。

std::vector<std::uint32_t> data = ...;
std::atomic<std::uint32_t> sum{0};
sender auto s = bulk_chunked(just(), par, 100000,
    [&sum, &data](int begin, int end)
    {
        auto partial_sum = std::accumulate(data.begin() + begin, data.begin() + end, 0U);
        sum.fetch_add(partial_sum);
    });
// the atomic object will not be touched 100000 times; will execute faster than bulk()