5 #include <libcopp/utils/config/libcopp_build_features.h>
23 LIBCOPP_COPP_NAMESPACE_BEGIN
26 template <
class T,
class... TARGS,
typename std::enable_if<!std::is_array<T>::value,
int>::type = 0>
28 return std::unique_ptr<T>(
new T(std::forward<TARGS>(args)...));
31 template <class T, typename std::enable_if<std::is_array<T>::value && std::extent<T>::value == 0,
int>::type = 0>
33 using TELEM =
typename std::remove_extent<T>::type;
34 return std::unique_ptr<T>(
new TELEM[sz]());
37 template <
class T,
class... TARGS,
typename std::enable_if<std::extent<T>::value != 0,
int>::type = 0>
56 using type = std::unique_ptr<void, small_object_optimize_storage_deleter<void> >;
63 std::unique_ptr<T, std::default_delete<T> > >::
type;
71 using type = std::unique_ptr<void, small_object_optimize_storage_deleter<void> >;
78 std::shared_ptr<T> >::
type;
81 template <
class T,
class TPTR>
85 struct LIBCOPP_COPP_API_HEAD_ONLY
86 poll_storage_base<void, std::unique_ptr<void, small_object_optimize_storage_deleter<void> > >
87 :
public std::true_type {
89 using ptr_type = std::unique_ptr<void, small_object_optimize_storage_deleter<void> >;
94 template <
class U,
class UDELETOR,
95 typename std::enable_if<std::is_convertible<typename std::decay<U>::type,
bool>::value,
bool>::type =
false>
97 std::unique_ptr<U, UDELETOR> &&in) LIBCOPP_MACRO_NOEXCEPT {
99 out.reset(
reinterpret_cast<void *
>(&out));
106 typename std::enable_if<std::is_convertible<typename std::decay<U>::type,
bool>::value,
bool>::type =
false>
109 out.reset(
reinterpret_cast<void *
>(&out));
117 out.reset(
reinterpret_cast<void *
>(&out));
133 r.reset(
reinterpret_cast<void *
>(&r));
135 l.reset(
reinterpret_cast<void *
>(&l));
145 struct LIBCOPP_COPP_API_HEAD_ONLY
poll_storage_base<T, std::unique_ptr<T, small_object_optimize_storage_deleter<T> > >
146 :
public std::true_type {
148 using ptr_type = std::unique_ptr<T, small_object_optimize_storage_deleter<T> >;
152 memset(&out.first, 0,
sizeof(out.first));
156 template <
class U,
class UDELETOR,
157 typename std::enable_if<std::is_base_of<T, typename std::decay<U>::type>::value ||
158 std::is_convertible<typename std::decay<U>::type, T>::value,
161 std::unique_ptr<U, UDELETOR> &&in) LIBCOPP_MACRO_NOEXCEPT {
164 out.second.reset(&out.first);
167 memset(&out.first, 0,
sizeof(out.first));
172 template <class U, typename std::enable_if<std::is_base_of<T, typename std::decay<U>::type>::value ||
173 std::is_convertible<typename std::decay<U>::type, T>::value,
177 out.second.reset(&out.first);
180 template <
class... U>
182 out.first =
value_type(std::forward<U>(in)...);
183 out.second.reset(&out.first);
188 out.first = in.first;
189 out.second.reset(&out.first);
192 memset(&out.first, 0,
sizeof(out.first));
202 if (!!l.second == !!r.second) {
208 r.second.reset(&r.first);
210 l.second.reset(&l.first);
216 return storage.second;
221 template <
class T,
class TPTR>
229 template <
class U,
class UDELETOR,
230 typename std::enable_if<std::is_base_of<T, typename std::decay<U>::type>::value,
bool>::type =
false>
232 std::unique_ptr<U, UDELETOR> &&in) LIBCOPP_MACRO_NOEXCEPT {
236 template <class U, typename std::enable_if<std::is_base_of<T, typename std::decay<U>::type>::value &&
240 out = std::move(std::static_pointer_cast<typename ptr_type::element_type>(in));
243 template <
class... U>
245 out.reset(
new value_type(std::forward<U>(in)...));
259 template <
class T,
class TPTR>
263 struct LIBCOPP_COPP_API_HEAD_ONLY
compact_storage<T, std::unique_ptr<T, small_object_optimize_storage_deleter<T> > >
264 :
public std::true_type {
266 using ptr_type = std::unique_ptr<T, small_object_optimize_storage_deleter<T> >;
274 memset(&out, 0,
sizeof(out));
278 construct_default_storage(out);
281 template <
class U,
class UDELETOR,
282 typename std::enable_if<std::is_base_of<T, typename std::decay<U>::type>::value ||
283 std::is_convertible<typename std::decay<U>::type, T>::value,
286 std::unique_ptr<U, UDELETOR> &&in) LIBCOPP_MACRO_NOEXCEPT {
290 memset(&out, 0,
sizeof(out));
294 template <class U, typename std::enable_if<std::is_base_of<T, typename std::decay<U>::type>::value ||
295 std::is_convertible<typename std::decay<U>::type, T>::value,
302 memcpy(&out, &in,
sizeof(out));
306 memcpy(&out, &in,
sizeof(out));
307 memset(&in, 0,
sizeof(in));
326 struct LIBCOPP_COPP_API_HEAD_ONLY
compact_storage<T, std::shared_ptr<T> > :
public std::false_type {
335 template <
class U,
class UDELETOR,
336 typename std::enable_if<std::is_base_of<T, typename std::decay<U>::type>::value,
bool>::type =
false>
346 typename std::enable_if<std::is_base_of<T, typename std::decay<U>::type>::value,
bool>::type =
false>
349 out = std::static_pointer_cast<T>(in);
355 template <
class... TARGS>
357 out = std::make_shared<T>(std::forward<TARGS>(in)...);
370 return storage.get();
377 using type = compact_storage<T, typename compact_storage_selector<T>::type>;
380 template <
class TOK,
class TERR,
bool is_all_trivial>
383 template <
class TOK,
class TERR>
389 EN_RESULT_SUCCESS = 0,
397 return is_success() ? &success_data_ :
nullptr;
400 return is_success() ? &success_data_ :
nullptr;
403 return is_error() ? &error_data_ :
nullptr;
408 template <
class UOK,
class UERR>
410 template <
class TRESULT,
bool>
413 template <
class TARGS>
415 make_success_base(std::forward<TARGS>(args));
418 template <
class TARGS>
420 make_error_base(std::forward<TARGS>(args));
423 template <
class TARGS>
425 success_data_ = args;
426 mode_ = EN_RESULT_SUCCESS;
429 template <
class TARGS>
432 mode_ = EN_RESULT_ERROR;
438 swap(success_data_, other.success_data_);
440 swap(error_data_, other.error_data_);
442 swap(mode_, other.mode_);
455 template <
class TOK,
class TERR>
461 EN_RESULT_SUCCESS = 0,
470 return is_success() ? success_storage_type::unwrap(success_data_) :
nullptr;
473 return is_success() ? success_storage_type::unwrap(success_data_) :
nullptr;
476 return is_error() ? error_storage_type::unwrap(error_data_) :
nullptr;
479 return is_error() ? error_storage_type::unwrap(error_data_) :
nullptr;
483 success_storage_type::construct_default_storage(success_data_);
484 error_storage_type::construct_default_storage(error_data_);
489 success_storage_type::construct_default_storage(success_data_);
490 error_storage_type::construct_default_storage(error_data_);
505 swap(mode_, other.mode_);
511 template <
class UOK,
class UERR>
513 template <
class TRESULT,
bool>
516 template <
class... TARGS>
519 success_storage_type::construct_storage(success_data_, std::forward<TARGS>(args)...);
520 mode_ = EN_RESULT_SUCCESS;
523 template <
class... TARGS>
526 error_storage_type::construct_storage(error_data_, std::forward<TARGS>(args)...);
527 mode_ = EN_RESULT_ERROR;
530 template <
class... TARGS>
533 make_object<success_storage_type>(success_data_, std::forward<TARGS>(args)...);
534 mode_ = EN_RESULT_SUCCESS;
537 template <
class... TARGS>
540 make_object<error_storage_type>(error_data_, std::forward<TARGS>(args)...);
541 mode_ = EN_RESULT_ERROR;
545 if (EN_RESULT_SUCCESS == mode_) {
546 success_storage_type::destroy_storage(success_data_);
547 }
else if (EN_RESULT_ERROR == mode_) {
548 error_storage_type::destroy_storage(error_data_);
551 mode_ = EN_RESULT_NONE;
555 template <
class TSTORAGE,
class... TARGS>
557 TSTORAGE::construct_storage(out, std::forward<TARGS>(args)...);
560 template <
class TSTORAGE,
class... TARGS>
562 TSTORAGE::construct_storage(out, std::make_shared<typename TSTORAGE::storage_type>(std::forward<TARGS>(args)...));
573 template <
class TRESULT,
bool>
576 template <
class TRESULT>
578 using type = std::unique_ptr<TRESULT>;
580 template <
class... TARGS>
582 type ret = LIBCOPP_COPP_NAMESPACE_ID::future::make_unique<TRESULT>();
584 ret->make_success_base(std::forward<TARGS>(args)...);
590 template <
class... TARGS>
592 type ret = LIBCOPP_COPP_NAMESPACE_ID::future::make_unique<TRESULT>();
594 ret->make_error_base(std::forward<TARGS>(args)...);
601 template <
class TRESULT>
605 template <
class... TARGS>
608 ret.make_success_base(std::forward<TARGS>(args)...);
612 template <
class... TARGS>
615 ret.make_error_base(std::forward<TARGS>(args)...);
620 template <
class TOK,
class TERR>
622 :
public result_base<TOK, TERR, default_compact_storage<TOK>::value && default_compact_storage<TERR>::value> {
634 template <
class... TARGS>
637 ret.construct_success(std::forward<TARGS>(args)...);
641 template <
class... TARGS>
644 ret.construct_error(std::forward<TARGS>(args)...);
649 template <
class... TARGS>
651 return _make_instance_type::make_success(std::forward<TARGS>(args)...);
654 template <
class... TARGS>
656 return _make_instance_type::make_error(std::forward<TARGS>(args)...);
660 LIBCOPP_COPP_NAMESPACE_END
UTIL_FORCEINLINE const error_type * get_error() const LIBCOPP_MACRO_NOEXCEPT
UTIL_FORCEINLINE bool is_error() const LIBCOPP_MACRO_NOEXCEPT
UTIL_FORCEINLINE void swap(result_base &other) LIBCOPP_MACRO_NOEXCEPT
UTIL_FORCEINLINE const success_type * get_success() const LIBCOPP_MACRO_NOEXCEPT
UTIL_FORCEINLINE success_type * get_success() LIBCOPP_MACRO_NOEXCEPT
UTIL_FORCEINLINE friend void swap(result_base &l, result_base &r) LIBCOPP_MACRO_NOEXCEPT
success_storage_type::storage_type success_data_
UTIL_FORCEINLINE void make_error_base(TARGS &&...args)
UTIL_FORCEINLINE error_type * get_error() LIBCOPP_MACRO_NOEXCEPT
UTIL_FORCEINLINE void make_success_base(TARGS &&...args)
static UTIL_FORCEINLINE void make_object(std::shared_ptr< typename TSTORAGE::storage_type > &out, TARGS &&...args)
static UTIL_FORCEINLINE void make_object(typename TSTORAGE::storage_type &out, TARGS &&...args)
result_base & operator=(result_base &&other)
UTIL_FORCEINLINE void construct_error(TARGS &&...args)
error_storage_type::storage_type error_data_
typename default_compact_storage< success_type >::type success_storage_type
typename default_compact_storage< error_type >::type error_storage_type
UTIL_FORCEINLINE bool is_success() const LIBCOPP_MACRO_NOEXCEPT
result_base(result_base &&other)
UTIL_FORCEINLINE void construct_success(TARGS &&...args)
UTIL_FORCEINLINE const error_type * get_error() const LIBCOPP_MACRO_NOEXCEPT
UTIL_FORCEINLINE success_type * get_success() LIBCOPP_MACRO_NOEXCEPT
UTIL_FORCEINLINE void construct_error(TARGS &&args) LIBCOPP_MACRO_NOEXCEPT
UTIL_FORCEINLINE bool is_error() const LIBCOPP_MACRO_NOEXCEPT
success_type success_data_
UTIL_FORCEINLINE error_type * get_error() LIBCOPP_MACRO_NOEXCEPT
UTIL_FORCEINLINE friend void swap(result_base &l, result_base &r) LIBCOPP_MACRO_NOEXCEPT
UTIL_FORCEINLINE void make_success_base(TARGS &&args) LIBCOPP_MACRO_NOEXCEPT
void swap(result_base &other) LIBCOPP_MACRO_NOEXCEPT
UTIL_FORCEINLINE void make_error_base(TARGS &&args) LIBCOPP_MACRO_NOEXCEPT
UTIL_FORCEINLINE void construct_success(TARGS &&args) LIBCOPP_MACRO_NOEXCEPT
UTIL_FORCEINLINE const success_type * get_success() const LIBCOPP_MACRO_NOEXCEPT
UTIL_FORCEINLINE bool is_success() const LIBCOPP_MACRO_NOEXCEPT
result_base< TOK, TERR, default_compact_storage< TOK >::value &&default_compact_storage< TERR >::value > base_type
static UTIL_FORCEINLINE self_type create_success(TARGS &&...args)
_make_result_instance_helper< self_type, poll_storage_base< base_type, typename poll_storage_ptr_selector< base_type >::type >::value > _make_instance_type
typename _make_instance_type::type storage_type
static UTIL_FORCEINLINE storage_type make_success(TARGS &&...args)
static UTIL_FORCEINLINE self_type create_error(TARGS &&...args)
static UTIL_FORCEINLINE storage_type make_error(TARGS &&...args)
导入继承关系约束 Licensed under the MIT licenses.
#define EXPLICIT_NODISCARD_ATTR
nodiscard, 标记禁止忽略返回值 usage: EXPLICIT_NODISCARD_ATTR int a; class EXPLICIT_NODISCARD_ATTR a; EXPLICIT_...
EXPLICIT_NODISCARD_ATTR std::unique_ptr< T > make_unique(TARGS &&...args)
class LIBCOPP_COPP_API_HEAD_ONLY result_base
struct LIBCOPP_COPP_API_HEAD_ONLY poll_storage_ptr_selector
struct LIBCOPP_COPP_API_HEAD_ONLY _make_result_instance_helper
struct LIBCOPP_COPP_API_HEAD_ONLY compact_storage
std::shared_ptr< cli::cmd_option_value > value_type
void swap(intrusive_ptr< T > &lhs, intrusive_ptr< T > &rhs)
static type make_success(TARGS &&...args)
std::unique_ptr< TRESULT > type
static type make_error(TARGS &&...args)
static UTIL_FORCEINLINE type make_error(TARGS &&...args)
static UTIL_FORCEINLINE type make_success(TARGS &&...args)
static UTIL_FORCEINLINE void construct_default_storage(storage_type &out)
static UTIL_FORCEINLINE void clone_storage(storage_type &out, const storage_type &in)
std::shared_ptr< T > ptr_type
static UTIL_FORCEINLINE value_type * unwrap(storage_type &storage) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void construct_storage(storage_type &out, TARGS &&...in)
static UTIL_FORCEINLINE bool is_shared_storage() LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void destroy_storage(storage_type &out)
static UTIL_FORCEINLINE void move_storage(storage_type &out, storage_type &&in) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void construct_storage(storage_type &out, std::unique_ptr< U, UDELETOR > &&in)
static UTIL_FORCEINLINE void swap(storage_type &l, storage_type &r) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE ptr_type clone_ptr(storage_type &storage) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void construct_storage(storage_type &out, std::shared_ptr< U > &&in)
static UTIL_FORCEINLINE const value_type * unwrap(const storage_type &storage) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void clone_storage(storage_type &out, const storage_type &in) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE ptr_type clone_ptr(storage_type &storage) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void construct_storage(storage_type &out, U &&in) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void construct_storage(storage_type &out) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE value_type * unwrap(storage_type &storage) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void construct_storage(storage_type &out, std::unique_ptr< U, UDELETOR > &&in) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void destroy_storage(storage_type &)
static UTIL_FORCEINLINE void swap(storage_type &l, storage_type &r) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE const value_type * unwrap(const storage_type &storage) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void construct_default_storage(storage_type &out) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void move_storage(storage_type &out, storage_type &&in) LIBCOPP_MACRO_NOEXCEPT
std::unique_ptr< T, small_object_optimize_storage_deleter< T > > ptr_type
static UTIL_FORCEINLINE bool is_shared_storage() LIBCOPP_MACRO_NOEXCEPT
std::unique_ptr< void, small_object_optimize_storage_deleter< void > > type
typename std::conditional< COPP_IS_TIRVIALLY_COPYABLE_V(T) &&sizeof(T)<=(sizeof(size_t)<< 2), std::unique_ptr< T, small_object_optimize_storage_deleter< T > >, std::shared_ptr< T > >::type type
compact_storage< T, typename compact_storage_selector< T >::type > type
std::unique_ptr< T, small_object_optimize_storage_deleter< T > > ptr_type
static UTIL_FORCEINLINE void construct_default_storage(storage_type &out) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void construct_storage(storage_type &out, U &&in) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void construct_storage(storage_type &out, U &&...in) LIBCOPP_MACRO_NOEXCEPT
std::pair< T, ptr_type > storage_type
static UTIL_FORCEINLINE void reset(storage_type &storage) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void construct_storage(storage_type &out, std::unique_ptr< U, UDELETOR > &&in) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void move_storage(storage_type &out, storage_type &&in) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE ptr_type & unwrap(storage_type &storage) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE const ptr_type & unwrap(const storage_type &storage) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void swap(storage_type &l, storage_type &r) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE const ptr_type & unwrap(const storage_type &storage) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE ptr_type & unwrap(storage_type &storage) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void swap(storage_type &l, storage_type &r) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void move_storage(storage_type &out, storage_type &&in) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void construct_storage(storage_type &out, std::unique_ptr< U, UDELETOR > &&in) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void construct_storage(storage_type &out, U &&in) LIBCOPP_MACRO_NOEXCEPT
std::unique_ptr< void, small_object_optimize_storage_deleter< void > > ptr_type
static UTIL_FORCEINLINE void reset(storage_type &storage) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void construct_default_storage(storage_type &out) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void reset(storage_type &storage) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE ptr_type & unwrap(storage_type &storage) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void construct_storage(storage_type &out, U &&...in) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void construct_storage(storage_type &out, std::unique_ptr< U, UDELETOR > &&in) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE const ptr_type & unwrap(const storage_type &storage) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void move_storage(storage_type &out, storage_type &&in) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void swap(storage_type &l, storage_type &r) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void construct_default_storage(storage_type &out) LIBCOPP_MACRO_NOEXCEPT
static UTIL_FORCEINLINE void construct_storage(storage_type &out, std::shared_ptr< U > &&in) LIBCOPP_MACRO_NOEXCEPT
std::unique_ptr< void, small_object_optimize_storage_deleter< void > > type
typename std::conditional< COPP_IS_TIRVIALLY_COPYABLE_V(T) &&sizeof(T)<(sizeof(size_t)<< 2), std::unique_ptr< T, small_object_optimize_storage_deleter< T > >, std::unique_ptr< T, std::default_delete< T > > >::type type
UTIL_FORCEINLINE void operator()(T *) const LIBCOPP_MACRO_NOEXCEPT
UTIL_FORCEINLINE void operator()(U *) const LIBCOPP_MACRO_NOEXCEPT
type_traits compatiable Licensed under the MIT licenses.
#define COPP_IS_TIRVIALLY_COPYABLE_V(X)