Iros
 
Loading...
Searching...
No Matches
filter.h
Go to the documentation of this file.
1#pragma once
2
20#include "di/function/invoke.h"
22#include "di/meta/algorithm.h"
23#include "di/meta/core.h"
24#include "di/meta/function.h"
25#include "di/meta/language.h"
26#include "di/util/addressof.h"
27#include "di/util/declval.h"
32
33namespace di::execution {
34namespace filter_ns {
35 template<typename T>
37
38 template<typename Env, typename... Sends>
45 SetStopped()>>>;
46
47 template<typename Fun, typename Env>
48 struct ValueSigs {
49 template<typename... Values>
50 using Invoke = NonValueCompletions<Env, meta::InvokeResult<Fun, Values&...>>;
51 };
52
53 template<typename Seq, typename Fun, typename Env>
57
58 template<typename... Values>
60
61 template<typename Seq, typename Fun, typename Env>
63
64 template<concepts::LanguageFunction Sig>
65 using SigAsTuple =
67
68 template<typename Fun, typename Rec>
69 struct DataT {
70 struct Type {
71 [[no_unique_address]] Fun predicate;
72 [[no_unique_address]] Rec receiver;
73 };
74 };
75
76 template<concepts::MovableValue Fun, concepts::Receiver Rec>
78
79 struct Empty {};
80
81 template<typename... Types>
83
84 template<typename Send, typename Fun, typename Rec, typename R>
103
104 template<typename Send, typename Fun, typename Rec, typename R>
106
107 template<typename Send, typename Fun, typename Rec, typename R>
109 struct Type : ReceiverAdaptor<Type> {
111 friend Base;
112
114
115 auto base() const& -> R const& { return m_data->receiver; }
116 auto base() && -> R&& { return di::move(m_data->receiver); }
117
118 template<typename... Values>
119 void set_value(Values&&... values) && {
120 using Tuple = meta::DecayedTuple<SetValue, Values...>;
121 m_data->values.template emplace<Tuple>(SetValue {}, di::forward<Values>(values)...);
122
123 m_data->on_receive_value();
124 }
125
126 template<typename Error>
127 void set_error(Error&& error) && {
129 m_data->values.template emplace<Tuple>(SetError {}, di::forward<Error>(error));
130
131 m_data->on_receive_value();
132 }
133
134 void set_stopped() && {
136 m_data->values.template emplace<Tuple>(SetStopped {});
137
138 m_data->on_receive_value();
139 }
140
141 private:
143 };
144 };
145
146 template<typename Send, typename Fun, typename Rec, typename R>
148
149 template<typename Send, typename Fun, typename Rec, typename R>
151 struct Type : ReceiverAdaptor<Type> {
152 private:
153 using Base = ReceiverAdaptor<Type>;
154 friend Base;
155
156 public:
158
159 auto base() const& -> R const& { return m_data->receiver; }
160 auto base() && -> R&& { return di::move(m_data->receiver); }
161
162 void set_value(bool accept) && { m_data->on_filter_result(accept); }
163
164 private:
166 };
167 };
168
169 template<typename Send, typename Fun, typename Rec, typename R>
171
172 template<typename Send, typename Fun, typename Rec, typename R>
174 struct Type : ReceiverAdaptor<Type> {
175 private:
176 using Base = ReceiverAdaptor<Type>;
177 friend Base;
178
179 public:
181
182 auto base() const& -> R const& { return m_data->receiver; }
183 auto base() && -> R&& { return di::move(m_data->receiver); }
184
185 void set_value() && { m_data->on_sent_value(true); }
186 void set_stopped() && { m_data->on_sent_value(false); }
187
188 private:
190 };
191 };
192
193 template<typename Send, typename Fun, typename Rec, typename R>
195
197 template<typename... Values>
198 auto operator()(SetValue, Values&&... values) const {
199 return just(di::forward<Values>(values)...);
200 }
201
202 template<typename Error>
203 auto operator()(SetError, Error&& error) const {
204 return just_error(di::forward<Error>(error));
205 }
206
207 auto operator()(SetStopped) const { return just_stopped(); }
208 };
209
210 constexpr inline auto just_var = JustVarFunction {};
211
212 template<typename... Types>
213 using JustVar = decltype(just_var(declval<Types>()...));
214
215 template<typename Send, typename Fun, typename Rec, typename R>
218 public:
224
245
246 explicit Type(Send&& sender, Data* data, R receiver)
247 : m_data(data, di::move(receiver))
248 , m_op(connect(di::forward<Send>(sender), ItemReceiver(util::addressof(m_data)))) {
249 m_data.on_receive_value = [this] {
250 di::visit(
252 [](Empty) {},
253 [this](auto& values) {
254 di::apply(
255 [this](auto tag, auto&... values) {
256 if constexpr (concepts::SameAs<decltype(tag), SetValue>) {
257 using IntermediateSend = decltype(m_data.data->predicate(values...));
258 using IntermediateOp =
260
261 auto& op = m_intermediate_op.template emplace<IntermediateOp>(
263 return connect(m_data.data->predicate(values...),
264 IntermediateReceiver(util::addressof(m_data)));
265 }));
266 start(op);
267 } else {
268 using FinalSend =
269 meta::NextSenderOf<Rec, decltype(just_var(tag, di::move(values)...))>;
271
272 auto& op = m_final_op.template emplace<FinalOp>(di::DeferConstruct([&] {
273 return connect(
274 set_next(m_data.data->receiver, just_var(tag, di::move(values)...)),
275 FinalReceiver(di::addressof(m_data)));
276 }));
277 start(op);
278 }
279 },
280 values);
281 }),
282 m_data.values);
283 };
284
285 m_data.on_filter_result = [this](bool accept) {
286 if (accept) {
288 [](Empty) {},
289 [this](auto&& values) {
290 di::apply(
291 [this](auto tag, auto&&... values) {
292 if constexpr (SameAs<SetValue, decltype(tag)>) {
293 using FinalSend =
294 meta::NextSenderOf<Rec, decltype(just(di::move(values)...))>;
296
297 auto& op =
298 m_final_op.template emplace<FinalOp>(di::DeferConstruct([&] {
299 return connect(set_next(m_data.data->receiver,
300 just(di::move(values)...)),
301 FinalReceiver(di::addressof(m_data)));
302 }));
303 start(op);
304 }
305 },
306 values);
307 }),
308 di::move(m_data.values));
309 } else {
310 execution::set_value(di::move(m_data.receiver));
311 }
312 };
313
314 m_data.on_sent_value = [this](bool success) {
315 if (success) {
316 execution::set_value(di::move(m_data.receiver));
317 } else {
318 execution::set_stopped(di::move(m_data.receiver));
319 }
320 };
321 }
322
323 private:
324 friend void tag_invoke(Tag<start>, Type& self) { start(self.m_op); }
325
326 ItemData m_data;
328 IntermediateOps m_intermediate_op;
329 FinalOps m_final_op;
330 };
331 };
332
333 template<typename Send, typename Fun, typename Rec, typename R>
335
336 template<typename Send, typename Fun, typename Rec>
337 struct ItemSenderT {
338 struct Type {
339 using is_sender = void;
341
342 [[no_unique_address]] Send sender;
344
345 template<concepts::RemoveCVRefSameAs<Type> Self, typename R>
348 friend auto tag_invoke(types::Tag<connect>, Self&& self, R receiver) {
350 self.data, di::move(receiver));
351 }
352
353 auto tag_invoke(Tag<get_env>, Type const& self) { return make_env(get_env(self.sender)); }
354 };
355 };
356
357 template<typename Send, typename Fun, typename Rec>
359
360 template<typename Fun, typename Rec>
361 struct ReceiverT {
362 struct Type : ReceiverAdaptor<Type> {
363 private:
364 using Base = ReceiverAdaptor<Type>;
365 friend Base;
366
367 public:
368 explicit Type(Data<Fun, Rec>* data) : m_data(data) {}
369
370 auto base() & -> Rec& { return m_data->receiver; }
371 auto base() const& -> Rec const& { return m_data->receiver; }
372 auto base() && -> Rec&& { return di::move(m_data->receiver); }
373
374 template<concepts::Sender Next>
375 auto set_next(Next&& next) & -> concepts::NextSender auto {
376 return ItemSender<Next, Fun, Rec> { di::forward<Next>(next), m_data };
377 }
378
379 private:
380 Data<Fun, Rec>* m_data;
381 };
382 };
383
384 template<concepts::MovableValue Fun, concepts::Receiver Rec>
386
387 template<typename Seq, typename Fun, typename Rec>
390 public:
394
395 explicit Type(Seq&& sequence, Fun&& predicate, Rec receiver)
396 : m_data(di::forward<Fun>(predicate), di::move(receiver))
397 , m_op(subscribe(di::forward<Seq>(sequence), Receiver(util::addressof(m_data)))) {}
398
399 private:
400 friend void tag_invoke(types::Tag<start>, Type& self) { start(self.m_op); }
401
402 [[no_unique_address]] Data m_data;
404 };
405 };
406
407 template<typename Seq, typename Fun, typename Rec>
409
410 template<typename Seq, typename Fun>
411 struct SequenceT {
412 struct Type {
414
415 [[no_unique_address]] Seq sequence;
416 [[no_unique_address]] Fun predicate;
417
418 template<concepts::RemoveCVRefSameAs<Type> Self, typename Rec>
421 friend auto tag_invoke(types::Tag<subscribe>, Self&& self, Rec receiver) {
423 di::forward_like<Self>(self.sequence), di::forward_like<Self>(self.predicate), di::move(receiver));
424 }
425
426 template<concepts::RemoveCVRefSameAs<Type> Self, typename Env>
430 return {};
431 }
432
433 friend auto tag_invoke(types::Tag<get_env>, Type const& self) {
435 }
436 };
437 };
438
439 template<concepts::Sender Seq, concepts::MovableValue Fun>
441
442 struct Function {
443 template<concepts::Sender Seq, concepts::MovableValue Fun>
444 auto operator()(Seq&& sequence, Fun&& predicate) const -> concepts::SequenceSender auto {
447 "The return type of the filter function must be a sequence sender.");
448 return function::tag_invoke(*this, di::forward<Seq>(sequence), di::forward<Fun>(predicate));
449 } else {
450 return Sequence<Seq, Fun> { di::forward<Seq>(sequence), di::forward<Fun>(predicate) };
451 }
452 }
453 };
454}
455
470}
Definition function.h:365
Definition defer_construct.h:8
Definition tuple_forward_declaration.h:5
Definition variant_forward_declaration.h:6
#define DI_IMMOVABLE_NO_UNIQUE_ADDRESS
Definition compiler.h:15
A sender that can be returned from di::execution::set_next().
Definition sequence_sender.h:50
Definition receiver_of.h:25
Definition core.h:114
Definition sequence_sender.h:102
Definition sequence_sender.h:128
Definition tag_invoke.h:33
Definition filter.h:34
meta::Type< DataT< meta::Decay< Fun >, Rec > > Data
Definition filter.h:77
meta::MakeCompletionSignatures< Seq, Env, ExtraSignatures< Seq, Fun, Env >, DecayValues > Signatures
Definition filter.h:62
meta::MakeCompletionSignatures< dummy_ns::DummySenderOf< meta::CompletionSignaturesOf< Seq, Env > >, Env, CompletionSignatures<>, ValueSigs< Fun, Env >::template Invoke > ExtraSignatures
Definition filter.h:54
meta::AsTemplate< meta::DecayedTuple, meta::PushFront< meta::AsList< Sig >, meta::LanguageFunctionReturn< Sig > > > SigAsTuple
Definition filter.h:65
decltype(just_var(declval< Types >()...)) JustVar
Definition filter.h:213
meta::Type< ItemOperationStateT< Send, Fun, Rec, R > > ItemOperationState
Definition filter.h:334
meta::AsTemplate< CompletionSignatures, meta::Unique< meta::PushBack< meta::Transform< meta::Concat< meta::ErrorTypesOf< Sends, Env, meta::List >... >, meta::Compose< meta::BindFront< meta::Quote< meta::AsLanguageFunction >, SetError >, meta::Quote< meta::List > > >, SetStopped()> > > NonValueCompletions
Definition filter.h:39
meta::Type< ItemReceiverT< Send, Fun, Rec, R > > ItemReceiver
Definition filter.h:147
meta::Type< FinalReceiverT< Send, Fun, Rec, R > > FinalReceiver
Definition filter.h:194
constexpr auto just_var
Definition filter.h:210
meta::Decay< T > DecayedRValue
Definition filter.h:36
meta::Type< ItemDataT< Send, Fun, Rec, R > > ItemData
Definition filter.h:105
meta::AsTemplate< Variant, meta::Unique< meta::List< Empty, Types... > > > OptionalVariant
Definition filter.h:82
meta::Type< SequenceT< meta::RemoveCVRef< Seq >, meta::Decay< Fun > > > Sequence
Definition filter.h:440
meta::Type< IntermediateReceiverT< Send, Fun, Rec, R > > IntermediateReceiver
Definition filter.h:170
meta::Type< ReceiverT< meta::Decay< Fun >, Rec > > Receiver
Definition filter.h:385
CompletionSignatures< SetValue(DecayedRValue< Values >...)> DecayValues
Definition filter.h:59
meta::Type< OperationStateT< Seq, Fun, Rec > > OperationState
Definition filter.h:408
meta::Type< ItemSenderT< meta::RemoveCVRef< Send >, meta::Decay< Fun >, Rec > > ItemSender
Definition filter.h:358
Definition bulk.h:30
constexpr auto without
Specify a removal of an environment query override.
Definition make_env.h:127
constexpr auto set_next
Set the next sender of a sequence.
Definition sequence_sender.h:77
constexpr auto just_error
Definition just.h:87
constexpr auto start
Definition start.h:20
constexpr auto make_env
Create an environment with overrides for queries.
Definition make_env.h:147
constexpr auto filter
Filter the values of a sequence.
Definition filter.h:469
meta::Type< receiver_interface_ns::ReceiverAdaptor< Self, Base > > ReceiverAdaptor
Definition receiver_adaptor.h:236
constexpr auto set_stopped
Definition set_stopped.h:14
constexpr auto get_sequence_cardinality
A query that returns the cardinality of a sequence.
Definition get_sequence_cardinality.h:45
constexpr auto subscribe
Subscribe a receiver to a sequence.
Definition sequence_sender.h:234
constexpr auto next
Get the next value of a async range in a coroutine.
Definition async_range.h:52
decltype(make_env(util::declval< BaseEnv >(), util::declval< Withs >()...)) MakeEnv
Represent an environment with overrides for queries.
Definition make_env.h:189
constexpr auto get_env
Definition get_env.h:27
constexpr auto connect
Definition connect.h:42
constexpr auto set_value
Definition set_value.h:14
constexpr auto just_stopped
Definition just.h:88
constexpr auto just
Definition just.h:86
constexpr tag_invoke_detail::TagInvokeFn tag_invoke
Definition tag_invoke.h:22
constexpr auto curry_back
Definition curry_back.h:141
detail::ChainHelper< Funs... > Chain
Definition function.h:119
T::Type Type
Definition core.h:26
detail::ComposeHelper< Funs... > Compose
Definition function.h:99
Type< detail::AsTemplateHelper< Template, T > > AsTemplate
Definition algorithm.h:60
Conditional< concepts::LanguageArray< RemoveReference< T > >, RemoveExtent< RemoveReference< T > > *, Conditional< concepts::LanguageFunction< RemoveReference< T > >, AddPointer< RemoveReference< T > >, RemoveCVRef< T > > > Decay
Definition language.h:574
Type< detail::LikeHelper< T, U > > Like
Definition language.h:468
Type< detail::LanguageFunctionReturnHelper< Fun > > LanguageFunctionReturn
Definition language.h:77
Type< detail::AsListHelper< T > > AsList
Definition algorithm.h:48
decltype(execution::subscribe(util::declval< Send >(), util::declval< Rec >())) SubscribeResult
Definition sequence_sender.h:239
constexpr auto c_
A value of type Constexpr<val>.
Definition constexpr.h:252
Fold< Lst, List<>, detail::PushBackIfUnique > Unique
Definition algorithm.h:203
vocab::Tuple< meta::Decay< Types >... > DecayedTuple
Definition decayed_tuple.h:8
decltype(function::detail::invoke_impl(util::declval< Ts >()...)) InvokeResult
Definition invoke.h:64
decltype(execution::set_next(util::declval< meta::RemoveCVRef< Rec > & >(), util::declval< Send >())) NextSenderOf
Definition sequence_sender.h:82
GatherSignatures< execution::SetValue, Sender, Env, Tup, Var > ValueTypesOf
Definition value_types_of.h:14
Concat< L, List< T > > PushBack
Definition algorithm.h:86
Type< detail::MakeCompletionSignaturesHelper< ExtraSigs, meta::ValueTypesOf< Send, Env, SetValue, meta::List >, meta::Transform< meta::ErrorTypesOf< Send, Env, meta::List >, meta::Quote< SetError > >, meta::Conditional< meta::sends_stopped< Send, Env >, SetStopped, types::CompletionSignatures<> > > > MakeCompletionSignatures
Definition make_completion_signatures.h:36
Type< detail::ApplyHelper< F, T > > Apply
Definition function.h:55
detail::TransformHelper< List, Function >::Type Transform
Definition algorithm.h:186
decltype(execution::connect(util::declval< Send >(), util::declval< Rec >())) ConnectResult
Definition connect_result.h:7
di::meta::Decay< decltype(T)> Tag
Definition tag_invoke.h:28
Definition vocab.h:96
StatusCode< Erased< long > > Error
Definition error.h:8
Definition zstring_parser.h:9
auto declval() -> meta::AddRValueReference< T >
Definition declval.h:8
constexpr auto forward_like(U &&value) -> decltype(auto)
Definition forward_like.h:8
constexpr auto apply(F &&f, Tup &&tuple) -> decltype(detail::apply_impl(meta::MakeIndexSequence< meta::TupleSize< Tup > > {}, util::forward< F >(f), util::forward< Tup >(tuple)))
Definition apply.h:22
constexpr auto sequence
Definition sequence.h:34
constexpr auto visit(Vis &&visitor, Vars &&... variants) -> R
Definition visit.h:39
constexpr auto data
Definition data.h:51
constexpr auto overload
Definition overload.h:28
Defines the sequence sender concepts and related CPOs.
Definition sequence_sender.h:86
Definition set_error.h:6
Definition set_stopped.h:6
Definition set_value.h:6
Rec receiver
Definition filter.h:72
Fun predicate
Definition filter.h:71
Definition filter.h:69
Definition filter.h:79
void set_stopped() &&
Definition filter.h:186
void set_value() &&
Definition filter.h:185
Type(ItemData< Send, Fun, Rec, R > *data)
Definition filter.h:180
auto base() const &-> R const &
Definition filter.h:182
auto base() &&-> R &&
Definition filter.h:183
Definition filter.h:442
auto operator()(Seq &&sequence, Fun &&predicate) const -> concepts::SequenceSender auto
Definition filter.h:444
Type(ItemData< Send, Fun, Rec, R > *data)
Definition filter.h:157
auto base() &&-> R &&
Definition filter.h:160
auto base() const &-> R const &
Definition filter.h:159
void set_value(bool accept) &&
Definition filter.h:162
di::Function< void()> on_receive_value
Definition filter.h:98
meta::Apply< meta::Quote< OptionalVariant >, meta::Transform< meta::AsList< meta::CompletionSignaturesOf< Send, Env > >, meta::Quote< SigAsTuple > > > Values
Definition filter.h:88
Type(Data< Fun, Rec > *data, R receiver)
Definition filter.h:92
di::Function< void(bool)> on_sent_value
Definition filter.h:100
MakeEnv< meta::EnvOf< R > > Env
Definition filter.h:87
Values values
Definition filter.h:96
Data< Fun, Rec > * data
Definition filter.h:94
di::Function< void(bool)> on_filter_result
Definition filter.h:99
Type(Send &&sender, Data *data, R receiver)
Definition filter.h:246
filter_ns::FinalReceiver< Send, Fun, Rec, R > FinalReceiver
Definition filter.h:223
friend void tag_invoke(Tag< start >, Type &self)
Definition filter.h:324
filter_ns::ItemReceiver< Send, Fun, Rec, R > ItemReceiver
Definition filter.h:221
meta::AsTemplate< OptionalVariant, meta::Transform< meta::ValueTypesOf< Send, MakeEnv< meta::EnvOf< R > >, meta::List, meta::List >, meta::Chain< meta::BindBack< meta::Quote< meta::Transform >, meta::Quote< meta::AddLValueReference > >, meta::BindFront< meta::Quote< meta::Apply >, meta::Chain< meta::BindFront< meta::Quote< meta::InvokeResult >, Fun & >, meta::BindBack< meta::Quote< meta::ConnectResult >, IntermediateReceiver > > > > > > IntermediateOps
Definition filter.h:226
meta::AsTemplate< OptionalVariant, meta::Transform< meta::AsList< meta::CompletionSignaturesOf< Send, MakeEnv< meta::EnvOf< R > > > >, meta::Chain< meta::Quote< SigAsTuple >, meta::Quote< meta::AsList >, meta::BindFront< meta::Quote< meta::Apply >, meta::Chain< meta::Quote< JustVar >, meta::BindFront< meta::Quote< meta::NextSenderOf >, Rec >, meta::BindBack< meta::Quote< meta::ConnectResult >, FinalReceiver > > > > > > FinalOps
Definition filter.h:235
filter_ns::IntermediateReceiver< Send, Fun, Rec, R > IntermediateReceiver
Definition filter.h:222
filter_ns::Data< Fun, Rec > Data
Definition filter.h:219
meta::ConnectResult< Send, ItemReceiver > Op
Definition filter.h:225
filter_ns::ItemData< Send, Fun, Rec, R > ItemData
Definition filter.h:220
Type(ItemData< Send, Fun, Rec, R > *data)
Definition filter.h:113
ReceiverAdaptor< Type > Base
Definition filter.h:110
void set_error(Error &&error) &&
Definition filter.h:127
void set_value(Values &&... values) &&
Definition filter.h:119
void set_stopped() &&
Definition filter.h:134
auto base() const &-> R const &
Definition filter.h:115
auto base() &&-> R &&
Definition filter.h:116
Send sender
Definition filter.h:342
auto tag_invoke(Tag< get_env >, Type const &self)
Definition filter.h:353
friend auto tag_invoke(types::Tag< connect >, Self &&self, R receiver)
Definition filter.h:348
di::CompletionSignatures< SetValue(), SetStopped()> CompletionSignatures
Definition filter.h:340
void is_sender
Definition filter.h:339
Data< Fun, Rec > * data
Definition filter.h:343
auto operator()(SetError, Error &&error) const
Definition filter.h:203
auto operator()(SetValue, Values &&... values) const
Definition filter.h:198
auto operator()(SetStopped) const
Definition filter.h:207
friend void tag_invoke(types::Tag< start >, Type &self)
Definition filter.h:400
filter_ns::Data< Fun, Rec > Data
Definition filter.h:393
meta::SubscribeResult< Seq, Receiver > Op
Definition filter.h:392
Type(Seq &&sequence, Fun &&predicate, Rec receiver)
Definition filter.h:395
filter_ns::Receiver< Fun, Rec > Receiver
Definition filter.h:391
Type(Data< Fun, Rec > *data)
Definition filter.h:368
auto base() const &-> Rec const &
Definition filter.h:371
auto base() &-> Rec &
Definition filter.h:370
auto base() &&-> Rec &&
Definition filter.h:372
auto set_next(Next &&next) &-> concepts::NextSender auto
Definition filter.h:375
SequenceTag is_sender
Definition filter.h:413
Seq sequence
Definition filter.h:415
friend auto tag_invoke(types::Tag< subscribe >, Self &&self, Rec receiver)
Definition filter.h:421
Fun predicate
Definition filter.h:416
friend auto tag_invoke(types::Tag< get_env >, Type const &self)
Definition filter.h:433
friend auto tag_invoke(types::Tag< get_completion_signatures >, Self &&, Env &&) -> Signatures< meta::Like< Self, Seq >, Fun, MakeEnv< Env > >
Definition filter.h:428
NonValueCompletions< Env, meta::InvokeResult< Fun, Values &... > > Invoke
Definition filter.h:50
Definition function.h:70
Definition function.h:64
Definition core.h:5
Definition function.h:30
Definition completion_signuatures.h:7
Definition immovable.h:4