12 #include <initializer_list>
15 #include <type_traits>
20 #define TR2_OPTIONAL_REQUIRES(...) \
21 typename std::enable_if<__VA_ARGS__::value, bool>::type = false
30 template <std::
size_t I>
54 return static_cast<T&&
>(t);
60 static_assert(!std::is_lvalue_reference<T>::value,
"!!");
61 return static_cast<T&&
>(t);
71 #define TR2_OPTIONAL_ASSERTED_EXPRESSION(CHECK, EXPR) (EXPR)
73 #define TR2_OPTIONAL_ASSERTED_EXPRESSION(CHECK, EXPR) \
74 ((CHECK) ? (EXPR) : ([] { assert(!#CHECK); }(), (EXPR)))
77 #if defined(__CUDA_ARCH__)
78 #define TR2_OPTIONAL_HOST_CONSTEXPR
80 #define TR2_OPTIONAL_HOST_CONSTEXPR constexpr
86 #if (defined _MSC_VER)
89 return std::addressof(ref);
100 template <class X, size_t S = sizeof(std::declval<X&>().operator&())>
105 constexpr
static bool value = has_overload<T>(
true);
108 template <
typename T, TR2_OPTIONAL_REQUIRES(!has_overloaded_addressof<T>)>
113 template <
typename T, TR2_OPTIONAL_REQUIRES(has_overloaded_addressof<T>)>
115 return std::addressof(ref);
142 : logic_error{what_arg} {}
144 : logic_error{what_arg} {}
154 template <
class... Args>
168 template <
class... Args>
188 template <
class... Args>
195 std::is_constructible<T, std::initializer_list<U>>)>
197 std::initializer_list<U> il,
220 template <
class... Args>
227 std::is_constructible<T, std::initializer_list<U>>)>
229 std::initializer_list<U> il,
238 std::is_trivially_destructible<T>::value,
246 using OptionalBase =
typename std::conditional<
247 std::is_trivially_destructible<U>::value,
258 constexpr
bool initialized()
const noexcept {
259 return OptionalBase<T>::init_;
262 return std::addressof(OptionalBase<T>::storage_.value_);
264 constexpr
const T* dataptr()
const {
268 constexpr
const T& contained_val()
const& {
269 return OptionalBase<T>::storage_.value_;
271 constexpr T&& contained_val() && {
272 return std::move(OptionalBase<T>::storage_.value_);
274 constexpr T& contained_val() & {
return OptionalBase<T>::storage_.value_; }
276 void clear() noexcept {
277 if (initialized()) dataptr()->~T();
278 OptionalBase<T>::init_ =
false;
281 template <
class... Args>
282 void initialize(Args&&... args) noexcept(
283 noexcept(T(std::forward<Args>(args)...))) {
284 assert(!OptionalBase<T>::init_);
285 ::new (
static_cast<void*
>(dataptr())) T(std::forward<Args>(args)...);
286 OptionalBase<T>::init_ =
true;
289 template <
class U,
class... Args>
290 void initialize(std::initializer_list<U> il, Args&&... args) noexcept(
291 noexcept(T(il, std::forward<Args>(args)...))) {
292 assert(!OptionalBase<T>::init_);
293 ::new (
static_cast<void*
>(dataptr()))
294 T(il, std::forward<Args>(args)...);
295 OptionalBase<T>::init_ =
true;
302 constexpr
optional() noexcept : OptionalBase<T>() {};
306 if (rhs.initialized()) {
307 ::new (
static_cast<void*
>(dataptr())) T(*rhs);
308 OptionalBase<T>::init_ =
true;
313 std::is_nothrow_move_constructible<T>::value)
314 : OptionalBase<T>() {
315 if (rhs.initialized()) {
316 ::new (
static_cast<void*
>(dataptr())) T(std::move(*rhs));
317 OptionalBase<T>::init_ =
true;
327 template <
typename U = T,
333 std::is_convertible<U&&, T>)>
334 constexpr
optional(U&& u) : OptionalBase<T>(
std::forward<U>(u)) {}
337 template <
typename U = T,
343 !std::is_convertible<U&&, T>)>
344 explicit constexpr
optional(U&& u) : OptionalBase<T>(
std::forward<U>(u)) {}
346 template <
class... Args>
353 std::is_constructible<T, std::initializer_list<U>>)>
355 std::initializer_list<U> il,
369 if (initialized() ==
true && rhs.initialized() ==
false)
371 else if (initialized() ==
false && rhs.initialized() ==
true)
373 else if (initialized() ==
true && rhs.initialized() ==
true)
374 contained_val() = *rhs;
379 std::is_nothrow_move_assignable<T>::value &&
380 std::is_nothrow_move_constructible<T>::value) {
381 if (initialized() ==
true && rhs.initialized() ==
false)
383 else if (initialized() ==
false && rhs.initialized() ==
true)
384 initialize(std::move(*rhs));
385 else if (initialized() ==
true && rhs.initialized() ==
true)
386 contained_val() = std::move(*rhs);
390 template <
class U = T>
392 typename std::enable_if<
393 std::is_constructible<T, U>::value &&
396 (std::is_scalar<T>::value ||
399 std::is_assignable<T&, U>::value,
402 contained_val() = std::forward<U>(v);
404 initialize(std::forward<U>(v));
409 template <
class... Args>
412 initialize(std::forward<Args>(args)...);
415 template <
class U,
class... Args>
416 void emplace(std::initializer_list<U> il, Args&&... args) {
418 initialize<U, Args...>(il, std::forward<Args>(args)...);
423 std::is_nothrow_move_constructible<T>::value &&
424 noexcept(
std::swap(std::declval<T&>(), std::declval<T&>()))) {
425 if (initialized() ==
true && rhs.initialized() ==
false) {
426 rhs.initialize(std::move(**
this));
428 }
else if (initialized() ==
false && rhs.initialized() ==
true) {
429 initialize(std::move(*rhs));
431 }
else if (initialized() ==
true && rhs.initialized() ==
true) {
439 explicit constexpr
operator bool() const noexcept {
return initialized(); }
440 constexpr
bool has_value() const noexcept {
return initialized(); }
447 assert(initialized());
456 assert(initialized());
457 return contained_val();
461 assert(initialized());
481 return std::move(contained_val());
486 return *
this ? **this : detail_::convert<T>(constexpr_forward<V>(v));
493 : detail_::convert<T>(constexpr_forward<V>(v));
512 static_assert(
sizeof(T) == 0,
513 "optional references is ill-formed, \
514 consider use optional of a std::reference_wrapper of type T to \
515 hold a reference if you really need to");
517 static_assert(!std::is_same<T, nullopt_t>::value,
"bad T");
518 static_assert(!std::is_same<T, in_place_t>::value,
"bad T");
527 template <
typename U = T>
530 template <
typename U = T>
558 template <
typename U>
567 template <
typename U>
593 explicit constexpr
operator bool() const noexcept {
return ref !=
nullptr; }
595 constexpr
bool has_value() const noexcept {
return ref !=
nullptr; }
599 return *
this ? **this
601 constexpr_forward<V>(v));
605 void reset() noexcept { ref =
nullptr; }
610 static_assert(
sizeof(T) == 0,
"optional rvalue references disallowed");
616 return bool(x) != bool(y) ? false : bool(x) ==
false ? true : *x == *y;
626 return (!y) ? false : (!x) ?
true : *x < *y;
708 return bool(x) ? *x == v :
false;
713 return bool(x) ? v == *x :
false;
718 return bool(x) ? *x != v :
true;
723 return bool(x) ? v != *x :
true;
728 return bool(x) ? *x < v :
true;
733 return bool(x) ? v > *x :
true;
738 return bool(x) ? *x > v :
false;
743 return bool(x) ? v < *x :
false;
748 return bool(x) ? *x >= v :
false;
753 return bool(x) ? v <= *x :
false;
758 return bool(x) ? *x <= v :
true;
763 return bool(x) ? v >= *x :
true;
769 return bool(x) ? *x == v :
false;
774 return bool(x) ? v == *x :
false;
779 return bool(x) ? *x != v :
true;
784 return bool(x) ? v != *x :
true;
789 return bool(x) ? *x < v :
true;
794 return bool(x) ? v > *x :
true;
799 return bool(x) ? *x > v :
false;
804 return bool(x) ? v < *x :
false;
809 return bool(x) ? *x >= v :
false;
814 return bool(x) ? v <= *x :
false;
819 return bool(x) ? *x <= v :
true;
824 return bool(x) ? v >= *x :
true;
830 return bool(x) ? *x == v :
false;
835 return bool(x) ? v == *x :
false;
840 return bool(x) ? *x != v :
true;
845 return bool(x) ? v != *x :
true;
850 return bool(x) ? *x < v :
true;
855 return bool(x) ? v > *x :
true;
860 return bool(x) ? *x > v :
false;
865 return bool(x) ? v < *x :
false;
870 return bool(x) ? *x >= v :
false;
875 return bool(x) ? v <= *x :
false;
880 return bool(x) ? *x <= v :
true;
885 return bool(x) ? v >= *x :
true;
908 template <
typename T>
918 template <
typename T>
929 #undef TR2_OPTIONAL_REQUIRES
930 #undef TR2_OPTIONAL_ASSERTED_EXPRESSION
931 #undef TR2_OPTIONAL_HOST_CONSTEXPR
#define TR2_OPTIONAL_REQUIRES(...)
#define TR2_OPTIONAL_HOST_CONSTEXPR
#define TR2_OPTIONAL_ASSERTED_EXPRESSION(CHECK, EXPR)
bad_optional_access(const char *what_arg)
bad_optional_access(const std::string &what_arg)
constexpr optional() noexcept
constexpr optional(in_place_t, T &v) noexcept
constexpr optional(const optional &rhs) noexcept
constexpr optional(U &u) noexcept
void emplace(T &v) noexcept
void swap(optional< T & > &rhs) noexcept
constexpr std::decay< T >::type value_or(V &&v) const
constexpr bool has_value() const noexcept
optional(in_place_t, T &&)=delete
auto operator=(U &&rhs) noexcept -> typename std::enable_if<!std::is_same< typename std::decay< U >::type, optional< T & >>::value, optional & >::type=delete
constexpr T * operator->() const
constexpr optional(nullopt_t) noexcept
auto operator=(U &&rhs) noexcept -> typename std::enable_if< std::is_same< typename std::decay< U >::type, optional< T & >>::value, optional & >::type
optional & operator=(nullopt_t) noexcept
constexpr T & operator*() const
void emplace(T &&)=delete
constexpr T & value() const
void emplace(Args &&... args)
constexpr optional(in_place_t, std::initializer_list< U > il, Args &&... args)
void emplace(std::initializer_list< U > il, Args &&... args)
constexpr T value_or(V &&v) const &
auto operator=(U &&v) -> typename std::enable_if< std::is_constructible< T, U >::value &&!std::is_same< typename std::decay< U >::type, optional< T >>::value &&(std::is_scalar< T >::value||std::is_same< typename std::decay< U >::type, T >::value) &&std::is_assignable< T &, U >::value, optional & >::type
constexpr T && value() &&
optional & operator=(const optional &rhs)
constexpr T const & operator*() const &
constexpr bool has_value() const noexcept
optional & operator=(nullopt_t) noexcept
constexpr T const * operator->() const
constexpr T * operator->()
constexpr optional(nullopt_t) noexcept
constexpr T const & value() const &
constexpr optional() noexcept
constexpr optional(in_place_t, Args &&... args)
optional(const optional &rhs)
optional & operator=(optional &&rhs) noexcept(std::is_nothrow_move_assignable< T >::value &&std::is_nothrow_move_constructible< T >::value)
constexpr T value_or(V &&v) &&
constexpr T && operator*() &&
constexpr T & operator*() &
void swap(optional< T > &rhs) noexcept(std::is_nothrow_move_constructible< T >::value &&noexcept(std::swap(std::declval< T & >(), std::declval< T & >())))
constexpr optional(U &&u)
optional(optional &&rhs) noexcept(std::is_nothrow_move_constructible< T >::value)
constexpr T * static_addressof(T &ref)
constexpr std::remove_reference< T >::type && constexpr_move(T &&t) noexcept
constexpr struct cloudViewer::utility::trivial_init_t trivial_init
constexpr optional< typename std::decay< T >::type > make_optional(T &&v)
void swap(optional< T > &x, optional< T > &y) noexcept(noexcept(x.swap(y)))
constexpr bool operator<=(const optional< T > &x, const optional< T > &y)
constexpr bool operator<(const optional< T > &x, const optional< T > &y)
constexpr bool operator>=(const optional< T > &x, const optional< T > &y)
constexpr in_place_t in_place
constexpr nullopt_t nullopt
constexpr T && constexpr_forward(typename std::remove_reference< T >::type &t) noexcept
constexpr bool operator!=(const optional< T > &x, const optional< T > &y)
typename std::conditional< std::is_trivially_destructible< T >::value, constexpr_optional_base< typename std::remove_const< T >::type >, optional_base< typename std::remove_const< T >::type > >::type OptionalBase
constexpr bool operator>(const optional< T > &x, const optional< T > &y)
constexpr bool operator==(const optional< T > &x, const optional< T > &y)
Generic file read and write utility for python interface.
void swap(cloudViewer::core::SmallVectorImpl< T > &LHS, cloudViewer::core::SmallVectorImpl< T > &RHS)
Implement std::swap in terms of SmallVector swap.
constexpr constexpr_optional_base(in_place_t, std::initializer_list< U > il, Args &&... args)
constexpr constexpr_optional_base() noexcept
constexpr_storage_t< T > storage_
constexpr constexpr_optional_base(T &&v)
constexpr constexpr_optional_base(const T &v)
~constexpr_optional_base()=default
constexpr constexpr_optional_base(in_place_t, Args &&... args)
constexpr static bool has_overload(...)
constexpr static bool has_overload(bool)
constexpr static bool value
in_place_index_t()=default
in_place_type_t()=default
constexpr nullopt_t(init)
constexpr optional_base(T &&v)
constexpr optional_base(const T &v)
optional_base(in_place_t, Args &&... args)
constexpr optional_base() noexcept
optional_base(in_place_t, std::initializer_list< U > il, Args &&... args)
constexpr result_type operator()(argument_type const &arg) const
cloudViewer::utility::optional< T > argument_type
hash< T >::result_type result_type
hash< T >::result_type result_type
cloudViewer::utility::optional< T & > argument_type
constexpr result_type operator()(argument_type const &arg) const
constexpr constexpr_storage_t(trivial_init_t) noexcept
constexpr constexpr_storage_t(Args &&... args)
~constexpr_storage_t()=default
constexpr storage_t(Args &&... args)
constexpr storage_t(trivial_init_t) noexcept