Template Class Optional#

Nested Relationships#

Nested Types#

Class Documentation#

template<typename T>
class Optional#

The class template TRAP::Optional manages an optional contained value, i.e. a value that may or may not be present.

A common use case for optional is the return value of a function that may fail. As opposed to other approaches, such as std::pair<T, bool>, optional handles expensive-to-construct objects well and is more readable, as the intent is expressed explicitly.

Any instance of Optional<T> at any given point in time either contains a value or does not contain a value.

If an Optional<T> contains a value, the value is guaranteed to be allocated as part of the optional object footprint, i.e. no dynamic memory allocation ever takes place. Thus, an optional object models an object, not a pointer, even though operator*() and operator->() are defined.

When an object of type Optional<T> is contextually converted to bool, the conversion returns true if the object contains a value and false if it does not contain a value.

The optional object contains a value in the following conditions:

  • The object is initialized with/assigned from a value of type T or another optional that contains a value. The optional object does not contain a value in the following conditions:

  • The object is default-initialized.

  • The object is initialized with/assigned from a value of type TRAP::NullOptT or an optional object that does not contain a value.

  • The member function Reset() is called.

This implementation supports references with rebinding on assignment.

There are no optional functions, arrays, or cv void; a program is ill-formed if it instantiates an optional with such type. In addition, a program is ill-formed if it instantiates an optional with the (possibly cv-qualified) tag types TRAP::NullOptT or TRAP::InPlaceT.

Template Parameters:

T – The type of the value to manage initialization state for. The type must meet the requiremnts of Destructible (in particular, array types are not allowed).

Public Types

using value_type = T#

Public Functions

inline constexpr Optional() noexcept#

Constructs a new optional object.

   Constructs an object that does not contain a value.
inline constexpr Optional(NullOptT) noexcept#

Constructs a new optional object.

   Constructs an object that does not contain a value.
constexpr Optional(const Optional &other) = default#

Constructs a new optional object.

   Copy constructor: If other contains a value, initializes the contained value as if direct-initializing
   (but not direct-list-initializing) an object of type T with the expression *other. If other does not
   contain a value, constructs an object that does not contain a value.

Parameters:

other – Another optional object whose contained value is copied.

inline constexpr Optional(const Optional &other)

Constructs a new optional object.

   Copy constructor: If other contains a value, initializes the contained value as if direct-initializing
   (but not direct-list-initializing) an object of type T with the expression *other. If other does not
   contain a value, constructs an object that does not contain a value.

Parameters:

other – Another optional object whose contained value is copied.

constexpr Optional(Optional &&other) = default#

Constructs a new optional object.

   Move constructor: If other contains a value, initializes the contained value as if direct-initializing
   (but not direct-list-initializing) an object of type T with the expression std::move(*other) and does
   not make other empty: a moved-from TRAP::Optional still contains a value, but the value itself is
   moved from. If other does not contain a value, constructs an object that does not contain a value.

Parameters:

other – Another optional object whose contained value is copied.

inline constexpr Optional(Optional &&other) noexcept(std::is_nothrow_move_constructible_v<T>)

Constructs a new optional object.

   Move constructor: If other contains a value, initializes the contained value as if direct-initializing
   (but not direct-list-initializing) an object of type T with the expression std::move(*other) and does
   not make other empty: a moved-from TRAP::Optional still contains a value, but the value itself is
   moved from. If other does not contain a value, constructs an object that does not contain a value.

Parameters:

other – Another optional object whose contained value is copied.

template<typename U = T>
inline explicit(!std::is_convertible_v<U, T>) constexpr Optional(U &&u)#

Constructs a new optional object.

   Constructs an optional object that contains a value, initialized as if direct-initializing
   (but not direct-list-initializing) an object of type T with the expression std::forward<U>(value).

Parameters:

u – Value with which to initialize the contained value.

template<typename ...Args>
inline explicit constexpr Optional(InPlaceT, Args&&... args)#

Constructs a new optional object.

   Constructs an optional object that contains a value, initialized as if direct-initializing
   (but not direct-list-initializing) an object of type T from the arguments std::forward<Args>(args)....

Parameters:

args – Arguments with which to initialize the contained value.

template<typename U, typename ...Args>
inline explicit constexpr Optional(InPlaceT, std::initializer_list<U> il, Args&&... args)#

Constructs a new optional object.

   Constructs an optional object that contains a value, initialized as if direct-initializing
   (but not direct-list-initializing) an object of type T from the arguments il, std::forward<Args>(args)....

Parameters:
  • il – Initializer list with which to initialize the contained value.

  • args – Arguments with which to initialize the contained value.

template<typename U = T>
inline explicit(!std::is_convertible_v<const U&, T>) constexpr Optional(const Optional<U> &other)#

Constructs a new optional object.

   Converting copy constructor: If other does not contain a value, constructs an optional object that
   does not contain a value. Otherwise, constructs an optional object that contains a value, initialized
   as if direct-initializing (but not direct-list-initializing) an object of type T with the
   expression *other.

Parameters:

other – Another optional object whose contained value is copied.

template<typename U = T>
inline explicit(!std::is_convertible_v<U, T>) constexpr Optional(Optional<U> &&other)#

Constructs a new optional object.

   Converting move constructor: If other does not contain a value, constructs an optional object that does
   not contain a value. Otherwise, constructs an optional object that contains a value, initialized
   as if direct-initializing (but not direct-list-initializing) an object of type T with the expression
   std::move(*other).

Parameters:

other – Another optional object whose contained value is copied.

constexpr ~Optional() = default#

If the object contains a value and the type T is not trivially destructible, destroys the contained value by calling its destructor, as if by Value().T::~T(). Otherwise, does nothing.

inline constexpr ~Optional()

If the object contains a value and the type T is not trivially destructible, destroys the contained value by calling its destructor, as if by Value().T::~T(). Otherwise, does nothing.

inline constexpr Optional &operator=(NullOptT) noexcept#

Replaces contents of *this with the contents of other.

   If *this contains a value before the call, the contained value is destroyed by calling its destructor
   as if by Value().T::~T(). *this does not contain a value after this call.

Returns:

*this.

constexpr Optional &operator=(const Optional &other) = default#

Replaces contents of *this with the contents of other.

   Assigns the state of other.
   - If both *this and other do not contain a value, the function has no effect.
   - If *this contains a value, but other does not, then the contained value is destroyed by calling
     its destructor.
   - If other contains a value, then depending on whether *this contains a value, the contained value
     is either direct-initialized or assigned from *other.

Parameters:

other – Another optional object whose contained value to assign.

Returns:

*this.

inline constexpr Optional &operator=(const Optional &other)

Replaces contents of *this with the contents of other.

   Assigns the state of other.
   - If both *this and other do not contain a value, the function has no effect.
   - If *this contains a value, but other does not, then the contained value is destroyed by calling
     its destructor.
   - If other contains a value, then depending on whether *this contains a value, the contained value
     is either direct-initialized or assigned from *other.

Parameters:

other – Another optional object whose contained value to assign.

Returns:

*this.

constexpr Optional &operator=(Optional &&other) = default#

Replaces contents of *this with the contents of other.

   Assigns the state of other.
   - If both *this and other do not contain a value, the function has no effect.
   - If *this contains a value, but other does not, then the contained value is destroyed by calling
     its destructor.
   - If other contians a value, then depending on whether *this contains a value, the contained value
     is either direct-initialized or assigned from std::move(*other). Note that a moved-from optional
     still contains a value.

Parameters:

other – Another optional object whose contained value to assign.

Returns:

*this.

inline constexpr Optional &operator=(Optional &&other)

Replaces contents of *this with the contents of other.

   Assigns the state of other.
   - If both *this and other do not contain a value, the function has no effect.
   - If *this contains a value, but other does not, then the contained value is destroyed by calling
     its destructor.
   - If other contians a value, then depending on whether *this contains a value, the contained value
     is either direct-initialized or assigned from std::move(*other). Note that a moved-from optional
     still contains a value.

Parameters:

other – Another optional object whose contained value to assign.

Returns:

*this.

template<typename U = T>
inline constexpr Optional &operator=(U &&u)#

Replaces contents of *this with the contents of other.

   Perfect-forwarded assignment: depending on whether *this contains a value before the call, the
   contained value is either direct-initialized from std::forward<U>(value) or assigned from
   std::forward<U>(value).

Parameters:

u – Value to assign to the contained value.

Returns:

*this.

template<typename U>
inline constexpr Optional &operator=(const Optional<U> &u)#

Replaces contents of *this with the contents of other.

   Assigns the state of other.
   - If both *this and other do not contain a value, the function has no effect.
   - If *this contains a value, but other does not, then the contained value is destroyed by calling
     its destructor. *this does not contain a value after the call.
   - If other contains a value, then depending on whether *this contains value, the contained
     value is either direct-initialized or assigned from *other.

Parameters:

u – Another optional object whose contained value to assign.

Returns:

*this.

template<typename U>
inline constexpr Optional &operator=(Optional<U> &&u)#

Replaces contents of *this with the contents of other.

   Assigns the state of other.
   - If both *this and other do not contain a value, the function has no effect.
   - If *this contains a value, but other does not, then the contained value is destroyed by calling
     its destructor. *this does not contain a value after the call.
   - If other contains a value, then depending on whether *this contains value, the contained
     value is either direct-initialized or assigned from std::move(*other). Note that a moved-from
     optional still contains a value.

Parameters:

u – Another optional object whose contained value to assign.

Returns:

*this.

inline constexpr const T *operator->() const noexcept#

Accesses the contained value. The behavior is undefined if *this does not contain a value.

Returns:

Pointer to the contained value.

inline constexpr T *operator->() noexcept#

Accesses the contained value. The behavior is undefined if *this does not contain a value.

Returns:

Pointer to the contained value.

inline constexpr const T &operator*() const & noexcept#

Accesses the contained value. The behavior is undefined if *this does not contain a value.

Returns:

Reference to the contained value.

inline constexpr T &operator*() & noexcept#

Accesses the contained value. The behavior is undefined if *this does not contain a value.

Returns:

Reference to the contained value.

inline constexpr const T &&operator*() const && noexcept#

Accesses the contained value. The behavior is undefined if *this does not contain a value.

Returns:

Reference to the contained value.

inline constexpr T &&operator*() && noexcept#

Accesses the contained value. The behavior is undefined if *this does not contain a value.

Returns:

Reference to the contained value.

inline explicit constexpr operator bool() const noexcept#

Checks whether *this contains a value.

Returns:

true if *this contains a value, false if *this does not contain a value.

inline constexpr bool HasValue() const noexcept#

Checks whether *this contains a value.

Returns:

true if *this contains a value, false if *this does not contain a value.

inline constexpr T &Value() &#

If *this contains a value, returns a reference to the contained value. Otherwise, throws a TRAP::BadOptionalAccess exception.

Note

The dereference operator operator*() does not check if this optional contains a value, which may be more efficient than Value().

Returns:

Reference to the contained value.

inline constexpr const T &Value() const &#

If *this contains a value, returns a reference to the contained value. Otherwise, throws a TRAP::BadOptionalAccess exception.

Note

The dereference operator operator*() does not check if this optional contains a value, which may be more efficient than Value().

Returns:

Reference to the contained value.

inline constexpr T &&Value() &&#

If *this contains a value, returns a reference to the contained value. Otherwise, throws a TRAP::BadOptionalAccess exception.

Note

The dereference operator operator*() does not check if this optional contains a value, which may be more efficient than Value().

Returns:

Reference to the contained value.

inline constexpr const T &&Value() const &&#

If *this contains a value, returns a reference to the contained value. Otherwise, throws a TRAP::BadOptionalAccess exception.

Note

The dereference operator operator*() does not check if this optional contains a value, which may be more efficient than Value().

Returns:

Reference to the contained value.

template<typename U>
inline constexpr T ValueOr(U &&u) const &#

Returns the contained value if *this has a value, otherwise returns u.

Parameters:

u – The value to use in case *this is empty.

Returns:

The current value if *this has a value, or u otherwise.

template<typename U>
inline constexpr T ValueOr(U &&u) &&#

Returns the contained value if *this has a value, otherwise returns u.

Parameters:

u – The value to use in case *this is empty.

Returns:

The current value if *this has a value, or u otherwise.

template<typename ...Args>
inline constexpr void Emplace(Args&&... args)#

Construct the contained value in-place. If *this already contains a value before the call, the contained value is destroyed by calling its destructor.

Initializes the contained value by direct-initializing (but not direct-list-initializing) with std::forward<Args>(args)… as parameters.

Parameters:

args – The arguments to pass to the constructor.

Returns:

Reference to the new contained value.

template<typename U, typename ...Args>
inline constexpr void Emplace(std::initializer_list<U> il, Args&&... args)#

Construct the contained value in-place. If *this already contains a value before the call, the contained value is destroyed by calling its destructor.

Initializes the contained value by direct-initializing (but not direct-list-initializing) with std::forward<Args>(args)… as parameters.

Parameters:

args – The arguments to pass to the constructor.

Returns:

Reference to the new contained value.

inline constexpr void Swap(Optional &other) noexcept(std::is_nothrow_move_constructible_v<T> && std::is_nothrow_swappable_v<T>)#

Swaps the contents with those of other.

   - If neither *this nor other contain a value, the function has no effect.
   - If only one of *this and other contains a value (let's call this object in
     and the other un), the contained value of un is direct-initialized from std::move(*in),
     followed by destruction of the contained value of in as if by in->T::~T().
     After this call, in does not contain a value; un contains a value.
   - If both *this and other contain values, the contained values are exchanged.

Parameters:

other – The optional object to exchange the contents with

inline constexpr void Reset() noexcept#

If *this contains a value, destroy that value as if by Value().T::~T(). Otherwise, there are no effects. *this does not contain a value after this call.

inline constexpr Optional Take()#

Take the current value out of this optional, leaving it empty.

Returns:

Returns the current value.

template<typename F, typename Ret = std::remove_cv_t<std::invoke_result_t<F, T&>>>
inline constexpr auto Transform(F &&f) &#

If *this contains a value, invokes f with the contained value as an argument, and returns an TRAP::Optional that contains the result of that invocation; otherwise, returns an empty TRAP::Optional.

Parameters:

f – A suitable function or Callable object whose call signature returns a non-reference type.

Returns:

An TRAP::Optional containing the result of f or an empty TRAP::Optional, as described above.

template<typename F, typename Ret = std::remove_cv_t<std::invoke_result_t<F, const T&>>>
inline constexpr auto Transform(F &&f) const &#

If *this contains a value, invokes f with the contained value as an argument, and returns an TRAP::Optional that contains the result of that invocation; otherwise, returns an empty TRAP::Optional.

Parameters:

f – A suitable function or Callable object whose call signature returns a non-reference type.

Returns:

An TRAP::Optional containing the result of f or an empty TRAP::Optional, as described above.

template<typename F, typename Ret = std::remove_cv_t<std::invoke_result_t<F, T>>>
inline constexpr auto Transform(F &&f) &&#

If *this contains a value, invokes f with the contained value as an argument, and returns an TRAP::Optional that contains the result of that invocation; otherwise, returns an empty TRAP::Optional.

Parameters:

f – A suitable function or Callable object whose call signature returns a non-reference type.

Returns:

An TRAP::Optional containing the result of f or an empty TRAP::Optional, as described above.

template<typename F, typename Ret = std::remove_cv_t<std::invoke_result_t<F, const T>>>
inline constexpr auto Transform(F &&f) const &&#

If *this contains a value, invokes f with the contained value as an argument, and returns an TRAP::Optional that contains the result of that invocation; otherwise, returns an empty TRAP::Optional.

Parameters:

f – A suitable function or Callable object whose call signature returns a non-reference type.

Returns:

An TRAP::Optional containing the result of f or an empty TRAP::Optional, as described above.

template<typename F>
inline constexpr auto AndThen(F &&f) &#

If *this contains a value, invokes f with the contained value as an argument, and returns the result of that invocation; otherwise, returns an empty TRAP::Optional.

Parameters:

f – A suitable function or Callable object that returns an TRAP::Optional.

Returns:

The result of f or an empty TRAP::Optional, as described above.

template<typename F>
inline constexpr auto AndThen(F &&f) const &#

If *this contains a value, invokes f with the contained value as an argument, and returns the result of that invocation; otherwise, returns an empty TRAP::Optional.

Parameters:

f – A suitable function or Callable object that returns an TRAP::Optional.

Returns:

The result of f or an empty TRAP::Optional, as described above.

template<typename F>
inline constexpr auto AndThen(F &&f) &&#

If *this contains a value, invokes f with the contained value as an argument, and returns the result of that invocation; otherwise, returns an empty TRAP::Optional.

Parameters:

f – A suitable function or Callable object that returns an TRAP::Optional.

Returns:

The result of f or an empty TRAP::Optional, as described above.

template<typename F>
inline constexpr auto AndThen(F &&f) const &&#

If *this contains a value, invokes f with the contained value as an argument, and returns the result of that invocation; otherwise, returns an empty TRAP::Optional.

Parameters:

f – A suitable function or Callable object that returns an TRAP::Optional.

Returns:

The result of f or an empty TRAP::Optional, as described above.

template<typename F>
inline constexpr Optional<T> OrElse(F &&f) const &#

Returns *this if it contains a value. Otherwise, returns the result of f.

Parameters:

f – A function or Callable object that returns an TRAP::Optional<T>.

Returns:

*this or the result of f, as described above.

template<typename F>
inline constexpr Optional<T> OrElse(F &&f) &&#

Returns *this if it contains a value. Otherwise, returns the result of f.

Parameters:

f – A function or Callable object that returns an TRAP::Optional<T>.

Returns:

*this or the result of f, as described above.

template<typename F>
inline constexpr T ValueOrElse(F &&f) const &#

Returns the current value if it contains a value. Otherwise, returns the result of f.

Parameters:

f – A function or Callable object that returns an T.

Returns:

The current value or the result of f, as described above.

template<typename F>
inline constexpr T ValueOrElse(F &&f) &&#

Returns the current value if it contains a value. Otherwise, returns the result of f.

Parameters:

f – A function or Callable object that returns an T.

Returns:

The current value or the result of f, as described above.

template<typename F, typename U>
inline constexpr auto TransformOrElse(F &&f, U &&u) const &#

Returns the result of f if optional contains a value. Otherwise, returns the result of u.

Parameters:

f – A function or Callable object that returns an T.

Returns:

The current value or the result of u, as described above.

template<typename F, typename U>
inline constexpr auto TransformOrElse(F &&f, U &&u) &&#

Returns the result of f if optional contains a value. Otherwise, returns the result of u.

Parameters:

f – A function or Callable object that returns an T.

Returns:

The current value or the result of u, as described above.

template<typename F, typename U>
inline constexpr U TransformOr(F &&f, U &&u) const &#

Returns the result of f if optional contains a value. Otherwise, returns the value u.

Parameters:

f – A function or Callable object that returns an T.

Returns:

The current value or u, as described above.

template<typename F, typename U>
inline constexpr U TransformOr(F &&f, U &&u) &&#

Returns the result of f if optional contains a value. Otherwise, returns the value u.

Parameters:

f – A function or Callable object that returns an T.

Returns:

The current value or u, as described above.

Public Members

char m_dummy = 0#
T m_value#