YACLib
C++ library for concurrent tasks execution
Loading...
Searching...
No Matches
shared_future.hpp
Go to the documentation of this file.
1#pragma once
2
7#include <yaclib/fwd.hpp>
10
11namespace yaclib {
12
13template <typename V, typename T>
16
17 public:
18 static_assert(Check<V>(), "V should be valid");
19 static_assert(!std::is_same_v<V, typename T::Error>,
20 "V cannot be the same as the trait Error type, because callback dispatch would be ambiguous");
21 static_assert(std::is_copy_constructible_v<wrap_void_t<V>>, "Result should be copyable");
22
23 using Result = typename T::template Result<V>;
24
25 SharedFutureBase() = default;
26
28 return _core != nullptr;
29 }
30
33 return !_core->Empty();
34 }
35
36 [[nodiscard]] Result Get() && noexcept {
38 Wait(*this);
39 if (_core->GetRef() == 1) {
40 return std::move(_core->Get());
41 } else {
42 return _core->Get();
43 }
44 }
45
46 void Get() const&& = delete;
47
50 Wait(*this);
51 return _core->Get();
52 }
53
54 [[nodiscard]] Result Touch() && noexcept {
57 if (_core->GetRef() == 1) {
58 return std::move(_core->Get());
59 } else {
60 return _core->Get();
61 }
62 }
63
64 void Touch() const&& = delete;
65
69 return _core->Get();
70 }
71
72 template <typename Func>
73 [[nodiscard]] /*FutureOn*/ auto Then(IExecutor& e, Func&& f) const {
75 "better way is use ThenInline(...) instead of Then(MakeInline(), ...)");
76 static constexpr auto CoreT = CoreType::ToUnique | CoreType::Call;
77 return detail::SetCallback<CoreT, true>(_core, &e, std::forward<Func>(f));
78 }
79
80 void Detach() && noexcept {
81 _core = nullptr;
82 }
83
84 template <typename Func>
85 void SubscribeInline(Func&& f) const {
86 static constexpr auto CoreT = CoreType::Detach;
87 detail::SetCallback<CoreT, false>(_core, nullptr, std::forward<Func>(f));
88 }
89
90 template <typename Func>
91 void Subscribe(IExecutor& e, Func&& f) const {
93 "better way is use SubscribeInline(...) instead of Subscribe(MakeInline(), ...)");
94 static constexpr auto CoreT = CoreType::Detach | CoreType::Call;
95 detail::SetCallback<CoreT, true>(_core, &e, std::forward<Func>(f));
96 }
97
101
105
108
112
113 protected:
114 explicit SharedFutureBase(detail::SharedCorePtr<V, T> core) noexcept : _core{std::move(core)} {
115 }
116
118};
119
120extern template class SharedFutureBase<void, DefaultTrait>;
121
122template <typename V, typename T>
126
127 public:
128 using Base::Base;
129
131 }
132
133 template <typename Func>
134 [[nodiscard]] /*Future*/ auto ThenInline(Func&& f) const {
135 static constexpr auto CoreT = CoreType::ToUnique;
136 return detail::SetCallback<CoreT, false>(this->_core, nullptr, std::forward<Func>(f));
137 }
138};
139
140extern template class SharedFuture<>;
141
142template <typename V, typename T>
146
147 public:
148 using Base::Base;
149 using Base::Detach;
150 using Base::Then;
151
153 }
154
155 [[nodiscard]] SharedFuture<V, T> On(std::nullptr_t) && noexcept {
156 return {std::move(this->_core)};
157 }
158
159 template <typename Func>
160 [[nodiscard]] /*FutureOn*/ auto ThenInline(Func&& f) const {
161 static constexpr auto CoreT = CoreType::ToUnique;
162 return detail::SetCallback<CoreT, true>(this->_core, nullptr, std::forward<Func>(f));
163 }
164
165 template <typename Func>
166 [[nodiscard]] /*FutureOn*/ auto Then(Func&& f) const {
167 static constexpr auto CoreT = CoreType::ToUnique | CoreType::Call;
168 return detail::SetCallback<CoreT, true>(this->_core, nullptr, std::forward<Func>(f));
169 }
170
171 template <typename Func>
172 void Subscribe(Func&& f) const {
173 static constexpr auto CoreT = CoreType::Detach | CoreType::Call;
174 detail::SetCallback<CoreT, false>(this->_core, nullptr, std::forward<Func>(f));
175 }
176};
177
178extern template class SharedFutureOn<>;
179
180} // namespace yaclib
A intrusive pointer to objects with an embedded reference count.
void Detach() &&noexcept
SharedFutureBase(detail::SharedCorePtr< V, T > core) noexcept
Result Get() &&noexcept
const detail::SharedCorePtr< V, T > & GetCore() const noexcept
typename T::template Result< V > Result
auto Then(IExecutor &e, Func &&f) const
Result Touch() &&noexcept
void Subscribe(IExecutor &e, Func &&f) const
bool Valid() const noexcept
bool Ready() const noexcept
void Touch() const &&=delete
detail::SharedCorePtr< V, T > _core
detail::SharedCorePtr< V, T > & GetCore() noexcept
void SubscribeInline(Func &&f) const
detail::SharedHandle GetHandle() const noexcept
void Get() const &&=delete
auto Then(Func &&f) const
SharedFutureOn(detail::SharedCorePtr< V, T > core) noexcept
SharedFuture< V, T > On(std::nullptr_t) &&noexcept
auto ThenInline(Func &&f) const
void Subscribe(Func &&f) const
SharedFuture(detail::SharedCorePtr< V, T > core) noexcept
auto ThenInline(Func &&f) const
#define YACLIB_WARN(cond, message)
Definition log.hpp:74
#define YACLIB_ASSERT(cond)
Definition log.hpp:85
Contract< V, T > MakeContract()
Creates related future and promise.
Definition contract.hpp:25
YACLIB_INLINE std::enable_if_t<(... &&is_waitable_v< Waited >), void > Wait(Waited &... fs) noexcept
Wait until Ready becomes true.
Definition wait.hpp:18