Skip to content

Commit c93c826

Browse files
Set up bulk algorithm
1 parent 6365e7e commit c93c826

File tree

1 file changed

+98
-0
lines changed

1 file changed

+98
-0
lines changed
+98
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,98 @@
1+
// include/beman/execution/detail/bulk.hpp -*-C++-*-
2+
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
3+
4+
#ifndef INCLUDED_BEMAN_EXECUTION_DETAIL_SPLIT
5+
#define INCLUDED_BEMAN_EXECUTION_DETAIL_SPLIT
6+
7+
#include "beman/execution/detail/basic_sender.hpp"
8+
#include "beman/execution/detail/callable.hpp"
9+
#include "beman/execution/detail/completion_signatures_for.hpp"
10+
#include "beman/execution/detail/get_domain_early.hpp"
11+
#include "beman/execution/detail/make_sender.hpp"
12+
#include "beman/execution/detail/movable_value.hpp"
13+
#include "beman/execution/detail/product_type.hpp"
14+
#include "beman/execution/detail/sender.hpp"
15+
#include "beman/execution/detail/set_error.hpp"
16+
#include "beman/execution/detail/transform_sender.hpp"
17+
#include <beman/execution/detail/default_impls.hpp>
18+
#include <beman/execution/detail/impls_for.hpp>
19+
#include <beman/execution/detail/set_value.hpp>
20+
#include <algorithm>
21+
#include <concepts>
22+
#include <exception>
23+
#include <type_traits>
24+
#include <utility>
25+
26+
namespace beman::execution::detail {
27+
28+
struct bulk_t {
29+
30+
/*
31+
32+
decltype((sndr)) does not satisfy sender, or
33+
Shape does not satisfy integral, or
34+
decltype((f)) does not satisfy movable-value,
35+
*/
36+
template <class Sender, class Shape, class f>
37+
requires(::beman::execution::sender<Sender> && std::is_integral_v<Shape> &&
38+
::beman::execution::detail::movable_value<f>)
39+
auto operator()(Sender&& sndr, Shape&& shape, f&& fun) const {
40+
41+
auto domain{::beman::execution::detail::get_domain_early(sndr)};
42+
43+
return ::beman::execution::transform_sender(
44+
domain,
45+
::beman::execution::detail::make_sender(
46+
*this, ::beman::execution::detail::product_type<Shape, f>{shape, fun}, std::forward<Sender>(sndr)));
47+
}
48+
};
49+
50+
template <>
51+
struct impls_for<bulk_t> : ::beman::execution::detail::default_impls {
52+
53+
static constexpr auto complete = []<class Index, class State, class Rcvr, class Tag, class... Args>(
54+
Index, State& state, Rcvr& rcvr, Tag, Args&&... args) noexcept -> void
55+
requires(not::std::same_as<Tag, set_value_t> ||
56+
::beman::execution::detail::callable<
57+
Tag,
58+
Args...> /* expression f(auto(shape), args...) is well-formed. dont know if this is ok */)
59+
{
60+
if constexpr (std::same_as<Tag, set_value_t>) {
61+
auto& [shape, f] = state;
62+
63+
constexpr bool nothrow = noexcept(f(auto(shape), args...));
64+
65+
try {
66+
[&]() noexcept(nothrow) {
67+
for (decltype(auto(shape)) i = 0; i < shape; i++) {
68+
f(auto(i), args...);
69+
}
70+
Tag()(std::move(rcvr), std::forward<Args>(args)...);
71+
}();
72+
73+
} catch (...) {
74+
75+
::beman::execution::set_error(std::move(rcvr), std::current_exception());
76+
}
77+
} else {
78+
Tag()(std::move(rcvr), std::forward<Args>(args)...);
79+
}
80+
};
81+
};
82+
83+
template <class Shape, class f, class Sender, class Env>
84+
struct completion_signatures_for<
85+
::beman::execution::detail::
86+
basic_sender<::beman::execution::detail::bulk_t, ::beman::execution::detail::product_type<Shape, f>, Sender>,
87+
Env> {};
88+
89+
} // namespace beman::execution::detail
90+
91+
namespace beman::execution {
92+
93+
using ::beman::execution::detail::bulk_t;
94+
inline constexpr ::beman::execution::bulk_t bulk{};
95+
96+
} // namespace beman::execution
97+
98+
#endif

0 commit comments

Comments
 (0)