namespace std::execution {
struct starts_on_t { unspecified };
inline constexpr starts_on_t starts_on{};
}
概要
starts_onは、入力Senderを指定Schedulerに関連付けられた実行リソースに属する実行エージェント上で開始するSenderアダプタである。
効果
説明用の式schとsndrに対して、decltype((sch))がschedulerを満たさない、もしくはdecltype((sndr))がsenderを満たさないとき、呼び出し式starts_on(sch, sndr)は不適格となる。
そうでなければ、呼び出し式starts_on(sch, sndr)はschが1回だけ評価されることを除いて、下記と等価。
transform_sender(
query-with-default(get_domain, sch, default_domain()),
make-sender(starts_on, sch, sndr))
Senderアルゴリズムタグ starts_on
説明用の式out_sndrとenvに対して、型OutSndrをdecltype((out_sndr))とする。sender-for<OutSndr, starts_on_t> == falseのとき、式starts_on.transform_env(out_sndr, env)および式starts_on.transform_sender(out_sndr, env)はいずれも不適格となる。
そうでなければ、下記の通り。
-
式
starts_on.transform_env(out_sndr, env)は下記と等価。 -
式
starts_on.transform_sender(out_sndr, env)は下記と等価。auto&& [_, sch, sndr] = out_sndr; return let_value( schedule(sch), [sndr = std::forward_like<OutSndr>(sndr)]() mutable noexcept(is_nothrow_move_constructible_v<decay_t<OutSndr>>) { return std::move(sndr); });
カスタマイゼーションポイント
Senderアルゴリズム構築時に、Schedulerschに関連付けられた実行ドメインに対してexecution::transform_sender経由でSender変換が行われる。
デフォルト実行ドメインでは無変換。
Receiverとの接続(connect)時に、関連付けられた実行ドメインに対してexecution::transform_sender経由でSender変換が行われる。
デフォルト実行ドメインではstarts_on.transform_sender(out_sndr, env)が呼ばれ、前述仕様通りのSenderへと変換される。
説明用の式out_sndrをstarts_on(sch, sndr)の戻り値Senderとし、型OutSndrをdecltype((out_sndr))とする。式out_rcvrをsender_in<OutSndr, Env> == trueとなる環境Envに関連付けられたReceiverとする。out_sndrとout_rcvrとの接続(connect)結果Operation Stateへの左辺値参照をopとしたとき、
- 呼び出し
start(op)は、Schedulerschに関連付けられた実行リソースに属する実行エージェント上で入力Sendersndrを開始すべき。 sch上でのスケジューリングが失敗した場合、未規定の実行エージェント上でout_rcvrのエラー完了が行われるべき。
例
#include <thread>
#include <print>
#include <execution>
namespace ex = std::execution;
int main()
{
std::println("main#{}", std::this_thread::get_id());
ex::run_loop loop;
std::jthread worker{[&]{
std::println("start worker#{}", std::this_thread::get_id());
loop.run();
}};
ex::scheduler auto sch = loop.get_scheduler();
ex::sender auto sndr =
ex::starts_on(sch, ex::just(21))
| ex::then([](int n) {
std::println("on worker#{}", std::this_thread::get_id());
return n * 2;
});
auto [val] = std::this_thread::sync_wait(std::move(sndr)).value();
std::println("val={}", val);
loop.finish();
}
出力例
main#126057012819776
start worker#126057007023680
on worker#126057007023680
val=42
バージョン
言語
- C++26
処理系
- Clang: ??
- GCC: ??
- ICC: ??
- Visual C++: ??