YOrch 1.0.0
Loading...
Searching...
No Matches
context.hpp
Go to the documentation of this file.
1#pragma once
2
3#include <cstddef>
4#include <tuple>
5#include <type_traits>
6#include <utility>
7
8namespace yorch::detail {
9
10template <typename T, typename... Ts>
11inline constexpr std::size_t type_count_v = (std::size_t{0} + ... + (std::is_same_v<T, Ts> ? 1 : 0));
12
13template <typename... Ts>
14inline constexpr bool unique_types_v = ((type_count_v<Ts, Ts...> == 1) && ...);
15
16template <typename>
17inline constexpr bool no_prev_always_false_v = false;
18
19} // namespace yorch::detail
20
21namespace yorch {
22
27struct no_prev {
28 template <typename T>
29 [[nodiscard]] static constexpr bool contains() noexcept {
30 return false;
31 }
32
42 template <typename T>
43 constexpr auto get() const -> T& {
45 "no_prev does not carry a direct parent value");
46 }
47};
48
58template <typename T>
60 using stored_type = std::remove_reference_t<T>;
61 using type = std::remove_cv_t<stored_type>;
62
63 static_assert(!std::is_void_v<type>,
64 "prev_slot_view<T> requires a non-void payload type");
65
67 // NOLINTNEXTLINE(cppcoreguidelines-avoid-const-or-ref-data-members)
69
70 template <typename U>
71 [[nodiscard]] static constexpr bool contains() noexcept {
72 return std::is_same_v<std::remove_cv_t<U>, type>;
73 }
74
75 template <typename U>
76 constexpr stored_type& get() const noexcept {
77 static_assert(contains<U>(),
78 "Requested type is not present in the direct parent slot");
79 return ref;
80 }
81};
82
90template <typename T>
91[[nodiscard]] constexpr auto prev_slot(T& value) noexcept
93 return {value};
94}
95
104template <typename... Ts>
105struct context {
106 static_assert(detail::unique_types_v<Ts...>,
107 "yorch::context<Ts...> requires unique types");
108
110 std::tuple<Ts...> storage;
111
118 constexpr context()
119 requires (std::default_initializable<Ts> && ...)
120 = default;
121
126 template <typename... Us>
127 requires (sizeof...(Us) == sizeof...(Ts)) &&
128 std::constructible_from<std::tuple<Ts...>, Us&&...>
129 constexpr explicit context(Us&&... xs)
130 : storage(std::forward<Us>(xs)...) {}
131
137 template <typename T>
138 [[nodiscard]] static constexpr bool contains() noexcept {
139 return detail::type_count_v<T, Ts...> == 1;
140 }
141
148 template <typename T>
149 constexpr T& get() & noexcept {
150 static_assert(contains<T>(),
151 "T must appear exactly once in yorch::context");
152 return std::get<T>(storage);
153 }
154
155 template <typename T>
156 constexpr const T& get() const& noexcept {
157 static_assert(contains<T>(),
158 "T must appear exactly once in yorch::context");
159 return std::get<T>(storage);
160 }
161
162 template <typename T>
163 constexpr T&& get() && noexcept {
164 static_assert(contains<T>(),
165 "T must appear exactly once in yorch::context");
166 return std::get<T>(std::move(storage));
167 }
168
169 template <typename T>
170 constexpr const T&& get() const&& noexcept {
171 static_assert(contains<T>(),
172 "T must appear exactly once in yorch::context");
173 return std::get<T>(std::move(storage));
174 }
175};
176
186template <typename Ctx, typename Prev = no_prev>
188 // NOLINTNEXTLINE(cppcoreguidelines-avoid-const-or-ref-data-members)
189 Ctx& ctx;
190
192 Prev prev;
193
194 [[nodiscard]] constexpr Prev& prev_view() & noexcept {
195 return prev;
196 }
197
198 [[nodiscard]] constexpr const Prev& prev_view() const& noexcept {
199 return prev;
200 }
201};
202
203template <typename Ctx>
204struct exec_context<Ctx, no_prev> {
205 // NOLINTNEXTLINE(cppcoreguidelines-avoid-const-or-ref-data-members)
206 Ctx& ctx;
207
208 [[nodiscard]] constexpr no_prev prev_view() const noexcept {
209 return {};
210 }
211};
212
214template <>
215struct exec_context<void, no_prev> {
216 // NOLINTNEXTLINE(readability-convert-member-functions-to-static)
217 [[nodiscard]] constexpr no_prev prev_view() const noexcept {
218 return {};
219 }
220};
221
222template <typename Prev>
223struct exec_context<void, Prev> {
225 Prev prev;
226
227 [[nodiscard]] constexpr Prev& prev_view() & noexcept {
228 return prev;
229 }
230
231 [[nodiscard]] constexpr const Prev& prev_view() const& noexcept {
232 return prev;
233 }
234};
235
236} // namespace yorch
constexpr bool unique_types_v
Definition context.hpp:14
constexpr std::size_t type_count_v
Definition context.hpp:11
constexpr bool no_prev_always_false_v
Definition context.hpp:17
constexpr bool is_adapter_descriptor_v
Definition adapters.hpp:63
constexpr auto value(T &&v) -> value_t< std::remove_cvref_t< T > >
Wraps a value as an owning spec.
Definition specs.hpp:179
constexpr auto prev_slot(T &value) noexcept -> prev_slot_view< T >
Creates a borrowed view over a direct parent payload object.
Definition context.hpp:91
Statically typed context container with a compile-time schema.
Definition context.hpp:105
constexpr const T && get() const &&noexcept
Definition context.hpp:170
constexpr T && get() &&noexcept
Definition context.hpp:163
constexpr context(Us &&... xs)
Explicitly constructs the context from the provided objects.
Definition context.hpp:129
static constexpr bool contains() noexcept
Checks whether a type is present in this context schema.
Definition context.hpp:138
constexpr const T & get() const &noexcept
Definition context.hpp:156
std::tuple< Ts... > storage
Underlying storage whose element order matches Ts....
Definition context.hpp:110
constexpr T & get() &noexcept
Returns the stored object of type T.
Definition context.hpp:149
constexpr context()=default
Default-constructs the context.
constexpr no_prev prev_view() const noexcept
Definition context.hpp:208
constexpr Prev & prev_view() &noexcept
Definition context.hpp:227
Prev prev
Optional direct-parent payload view used by direct-parent access specs.
Definition context.hpp:225
constexpr const Prev & prev_view() const &noexcept
Definition context.hpp:231
constexpr no_prev prev_view() const noexcept
Definition context.hpp:217
Lightweight borrowed view used during execution.
Definition context.hpp:187
constexpr Prev & prev_view() &noexcept
Definition context.hpp:194
Prev prev
Optional direct-parent payload view used by direct-parent access specs.
Definition context.hpp:192
constexpr const Prev & prev_view() const &noexcept
Definition context.hpp:198
Sentinel view indicating that the current execution has no direct parent output.
Definition context.hpp:27
static constexpr bool contains() noexcept
Definition context.hpp:29
constexpr auto get() const -> T &
Always fails because no_prev carries no retrievable value.
Definition context.hpp:43
Lightweight borrowed view over a direct parent output slot.
Definition context.hpp:59
std::remove_reference_t< T > stored_type
Definition context.hpp:60
static constexpr bool contains() noexcept
Definition context.hpp:71
stored_type & ref
Borrowed reference to the direct parent payload.
Definition context.hpp:68
constexpr stored_type & get() const noexcept
Definition context.hpp:76
std::remove_cv_t< stored_type > type
Definition context.hpp:61