STX  1.0.0
List of all members
stx::Option< T > Struct Template Reference

#include <option_result.h>

Detailed Description

template<typename T>
struct stx::Option< T >

Optional values.

Type Option represents an optional value: every Option is either Some and contains a value, or None, and does not. They have a number of uses:

Option's are commonly paired with pattern matching to query the presence of a value and take action, always accounting for the Nones case.

auto divide = [](double numerator, double denominator) -> Option<double> {
if (denominator == 0.0) {
return None;
} else {
return Some(numerator / denominator);
}
};
// The return value of the function is an option
auto result = divide(2.0, 3.0);
result.match([](double& value) { std::cout << value << std::endl; },
[]() { std::cout << "has no value" << std::endl; });

Constexpr ?

C++ 20 and above

Member Typedef Documentation

◆ value_type

template<typename T>
using stx::Option< T >::value_type = T

Constructor & Destructor Documentation

◆ Option() [1/6]

template<typename T>
constexpr stx::Option< T >::Option ( )
inlinenoexcept

◆ Option() [2/6]

template<typename T>
constexpr stx::Option< T >::Option ( Some< T > &&  some)
inline

◆ Option() [3/6]

template<typename T>
constexpr stx::Option< T >::Option ( Some< T > const &  some)
inline

◆ Option() [4/6]

template<typename T>
constexpr stx::Option< T >::Option ( NoneType const &  )
inlinenoexcept

◆ Option() [5/6]

template<typename T>
stx::Option< T >::Option ( Option< T > &&  rhs)
inline

◆ Option() [6/6]

template<typename T>
stx::Option< T >::Option ( Option< T > const &  rhs)
inline

◆ ~Option()

template<typename T>
STX_CXX20_DESTRUCTOR_CONSTEXPR stx::Option< T >::~Option ( )
inlinenoexcept

Member Function Documentation

◆ AND()

template<typename T>
template<typename U >
constexpr auto stx::Option< T >::AND ( Option< U > &&  cmp) && -> Option<U>
inline

Returns None if the option is None, otherwise returns cmp.

Examples

Basic usage:

Option a = Some(2);
Option<string> b = None;
ASSERT_EQ(move(a).AND(move(b)), None);
Option<int> c = None;
Option d = Some("foo"s);
ASSERT_EQ(move(c).AND(move(d)), None);
Option e = Some(2);
Option f = Some("foo"s);
ASSERT_EQ(move(e).AND(move(f)), Some("foo"s));
Option<int> g = None;
Option<string> h = None;
ASSERT_EQ(move(g).AND(move(h)), None);

◆ and_then()

template<typename T>
template<typename Fn >
constexpr auto stx::Option< T >::and_then ( Fn &&  op) && -> invoke_result<Fn&&, T&&>
inline

Returns None if the option is None, otherwise calls op with the wrapped value and returns the result.

Some languages call this operation flatmap.

Examples

Basic usage:

auto sq = [] (auto x) -> Option<int> { return Some(x * x); };
auto nope = [] (auto) -> Option<int> { return None; };
ASSERT_EQ(make_some(2).and_then(sq).and_then(sq), Some(16));
ASSERT_EQ(make_some(2).and_then(sq).and_then(nope), None);
ASSERT_EQ(make_some(2).and_then(nope).and_then(sq), None);
ASSERT_EQ(make_none<int>().and_then(sq).and_then(sq), None);

◆ as_cref() [1/2]

template<typename T>
constexpr auto stx::Option< T >::as_cref ( ) const & -> Option<ConstRef<T>>
inlinenoexcept

Converts from Option<T> const& or Option<T> & to Option<ConstRef<T>>.

NOTE

ConstRef<T> is an alias for std::reference_wrapper<T const> and guides against reference-collapsing

◆ as_cref() [2/2]

template<typename T>
constexpr auto stx::Option< T >::as_cref ( ) const && -> Option< ConstRef< T >>=delete
deletenoexcept

◆ as_ref() [1/4]

template<typename T>
constexpr auto stx::Option< T >::as_ref ( ) & -> Option<MutRef<T>>
inlinenoexcept

Converts from Option<T> to Option<MutRef<T>>.

Examples

Basic usage:

auto mutate = [](Option<int>& r) {
r.as_ref().match([](Ref<int> ref) { ref.get() = 42; },
[]() { });
};
auto x = make_some(2);
mutate(x);
ASSERT_EQ(x, Some(42));
auto y = make_none<int>();
mutate(y);
ASSERT_EQ(y, None);

◆ as_ref() [2/4]

template<typename T>
constexpr auto stx::Option< T >::as_ref ( ) const & -> Option<ConstRef<T>>
inlinenoexcept

◆ as_ref() [3/4]

template<typename T>
constexpr auto stx::Option< T >::as_ref ( ) && -> Option< MutRef< T >>=delete
deletenoexcept

◆ as_ref() [4/4]

template<typename T>
constexpr auto stx::Option< T >::as_ref ( ) const && -> Option< ConstRef< T >>=delete
deletenoexcept

◆ clone()

template<typename T>
constexpr auto stx::Option< T >::clone ( ) const -> Option
inline

Returns a copy of the option and its contents.

Examples

Basic usage:

Option x = Some(8);
ASSERT_EQ(x, x.clone());

◆ contains()

template<typename T>
template<typename CmpType >
constexpr bool stx::Option< T >::contains ( CmpType const &  cmp) const
inline

Returns true if the option is a Some value containing the given value.

Examples

Basic usage:

Option x = Some(2);
ASSERT_TRUE(x.contains(2));
Option y = Some(3);
ASSERT_FALSE(y.contains(2));
Option<int> z = None;
ASSERT_FALSE(z.contains(2));

◆ exists()

template<typename T>
template<typename UnaryPredicate >
constexpr bool stx::Option< T >::exists ( UnaryPredicate &&  predicate) const
inline

Returns the value of evaluating the predicate on the contained value if the Option is a Some, else returns false.

Examples

Basic usage:

Option x = Some(2);
auto even = [](auto x) { return x == 2; };
ASSERT_TRUE(x.exists(even));

◆ expect()

template<typename T>
auto stx::Option< T >::expect ( std::string_view const &  msg) && -> T
inline

Unwraps an option, yielding the content of a Some.

Panics

Panics if the value is a None with a custom panic message provided by msg.

Examples

Basic usage:

Option x = Some("value"s);
ASSERT_EQ(move(x).expect("the world is ending"), "value");
Option<string> y = None;
ASSERT_DEATH(move(y).expect("the world is ending")); // panics with
// the world is
// ending

◆ expect_none()

template<typename T>
void stx::Option< T >::expect_none ( std::string_view const &  msg) &&
inline

Unwraps an option, expecting None and returning nothing.

Panics

Panics if the value is a Some, with a panic message.

Examples

Basic usage:

auto divide = [](double num, double denom) -> Option<double> {
if (denom == 0.0) return None;
return Some(num / denom);
};
ASSERT_DEATH(divide(0.0, 1.0).expect_none());
ASSERT_NO_THROW(divide(1.0, 0.0).expect_none());

◆ filter()

template<typename T>
template<typename UnaryPredicate >
constexpr auto stx::Option< T >::filter ( UnaryPredicate &&  predicate) && -> Option
inline

Returns None if the option is None, otherwise calls predicate with the wrapped value and returns:

  • Some<T> if predicate returns true on invocation on the value.
  • None if predicate returns false on invocation on the value.

filter() lets you decide which elements to keep.

Examples

Basic usage:

auto is_even = [](int n) -> bool { return n % 2 == 0; };
ASSERT_EQ(make_none<int>().filter(is_even), None);
ASSERT_EQ(make_some(3).filter(is_even), None);
ASSERT_EQ(make_some(4).filter(is_even), Some(4));

◆ filter_not()

template<typename T>
template<typename UnaryPredicate >
constexpr auto stx::Option< T >::filter_not ( UnaryPredicate &&  predicate) && -> Option
inline

Returns None if the option is None, otherwise calls predicate with the wrapped value and returns:

  • Some<T> if predicate returns false on invocation on the value.
  • None if predicate returns true on invocation on the value.

filter_not() lets you decide which elements to keep.

Examples

Basic usage:

auto is_even = [](int n) -> bool { return n % 2 == 0; };
ASSERT_EQ(make_none<int>().filter_not(is_even), None);
ASSERT_EQ(make_some(3).filter_not(is_even), Some(3));
ASSERT_EQ(make_some(4).filter_not(is_even), None);

◆ is_none()

template<typename T>
constexpr bool stx::Option< T >::is_none ( ) const
inlinenoexcept

Returns true if the option is a None value.

Examples

Basic usage:

Option x = Some(2);
ASSERT_FALSE(x.is_none());
Option<int> y = None;
ASSERT_TRUE(y.is_none());

◆ is_some()

template<typename T>
constexpr bool stx::Option< T >::is_some ( ) const
inlinenoexcept

Returns true if this Option is a Some value.

Examples

Basic usage:

Option x = Some(2);
ASSERT_TRUE(x.is_some());
Option<int> y = None;
ASSERT_FALSE(y.is_some());

◆ map()

template<typename T>
template<typename Fn >
constexpr auto stx::Option< T >::map ( Fn &&  op) && -> Option<invoke_result<Fn&&, T&&>>
inline

Maps an Option<T> to Option<U> by applying a function to a contained value and therefore, consuming/moving the contained value.

Examples

Basic usage:

Converts an Option<string> into an Option<size_t>, consuming the original:

Option maybe_string = Some("Hello, World!"s);
// `Option::map` will only work on Option as an r-value and assumes the
// object in it is about to be moved
auto maybe_len = move(maybe_string).map([](auto s){ return s.size();
});
// maybe_string is invalid and should not be used from here since we
// `std::move`-d from it
ASSERT_EQ(maybe_len, Some<size_t>(13));

◆ map_or()

template<typename T>
template<typename Fn , typename A >
constexpr auto stx::Option< T >::map_or ( Fn &&  op,
A &&  alt 
) && -> invoke_result<Fn&&, T&&>
inline

Applies a function to the contained value (if any), or returns the provided alternative (if not).

Examples

Basic usage:

Option x = Some("foo"s);
auto alt_fn = [](auto s) { return s.size(); };
ASSERT_EQ(move(x).map_or(alt_fn, 42UL), 3UL);
Option<string> y = None;
ASSERT_EQ(move(y).map_or(alt_fn, 42UL), 42UL);

◆ map_or_else()

template<typename T>
template<typename Fn , typename AltFn >
constexpr auto stx::Option< T >::map_or_else ( Fn &&  op,
AltFn &&  alt 
) && -> invoke_result<Fn&&, T&&>
inline

Applies a function to the contained value (if any), or computes a default (if not).

Examples

Basic usage:

size_t k = 21;
auto map_fn = [] (auto s) { return s.size(); };
auto alt_fn = [&k] () { return 2UL * k; };
Option x = Some("foo"s);
ASSERT_EQ(move(x).map_or_else(map_fn, alt_fn), 3);
Option<string> y = None;
ASSERT_EQ(move(y).map_or_else(map_fn, alt_fn), 42);

◆ match() [1/3]

template<typename T>
template<typename SomeFn , typename NoneFn >
constexpr auto stx::Option< T >::match ( SomeFn &&  some_fn,
NoneFn &&  none_fn 
) && -> invoke_result<SomeFn&&, T&&>
inline

Calls the parameter some_fn with the value if this Option is a Some<T> variant, else calls none_fn. This Option is consumed afterward.

The return type of both parameters must be convertible. They can also both return nothing ( void ).

Examples

Basic usage:

auto j = make_some("James"s).match([](string name) { return name; },
[]() { return "<unidentified>"s; });
ASSERT_EQ(j, "James"s);
auto k = make_none<string>().match([](string name) { return name; },
[]() { return "<unidentified>"s; });
ASSERT_EQ(k, "<unidentified>"s);

Notes

  • The Option's reference type is passed to the function arguments. i.e. If the Option is an r-value, r-value references are passed to the function arguments some_fn and none_fn.

◆ match() [2/3]

template<typename T>
template<typename SomeFn , typename NoneFn >
constexpr auto stx::Option< T >::match ( SomeFn &&  some_fn,
NoneFn &&  none_fn 
) & -> invoke_result<SomeFn&&, T&>
inline

◆ match() [3/3]

template<typename T>
template<typename SomeFn , typename NoneFn >
constexpr auto stx::Option< T >::match ( SomeFn &&  some_fn,
NoneFn &&  none_fn 
) const & -> invoke_result<SomeFn&&, T const&>
inline

◆ ok_or()

template<typename T>
template<typename E >
constexpr auto stx::Option< T >::ok_or ( error) && -> Result<T, E>
inline

Transforms the Option<T> into a Result<T, E>, mapping Some<T> to Ok<T> and None to Err<E>.

Arguments passed to ok_or are eagerly evaluated; if you are passing the result of a function call, it is recommended to use ok_or_else, which is lazily evaluated.

Examples

Basic usage:

Option x = Some("foo"s);
ASSERT_EQ(move(x).ok_or(0), Ok("foo"s));
Option<string> y = None;
ASSERT_EQ(move(y).ok_or(0), Err(0));

◆ ok_or_else()

template<typename T>
template<typename Fn >
constexpr auto stx::Option< T >::ok_or_else ( Fn &&  op) && -> Result<T, invoke_result<Fn&&>>
inline

Transforms the Option<T> into a Result<T, E>, mapping Some<T> to Ok<T> and None to Err(op()).

Examples

Basic usage:

auto else_fn = [] () { return 0; };
Option x = Some("foo"s);
ASSERT_EQ(move(x).ok_or_else(else_fn), Ok("foo"s));
Option<string> y = None;
ASSERT_EQ(move(y).ok_or_else(else_fn), Err(0));

◆ operator bool()

template<typename T>
stx::Option< T >::operator bool ( ) const
inlinenoexcept

◆ operator!=() [1/3]

template<typename T>
template<typename U >
constexpr bool stx::Option< T >::operator!= ( Option< U > const &  cmp) const
inline

◆ operator!=() [2/3]

template<typename T>
template<typename U >
constexpr bool stx::Option< T >::operator!= ( Some< U > const &  cmp) const
inline

◆ operator!=() [3/3]

template<typename T>
constexpr bool stx::Option< T >::operator!= ( NoneType const &  ) const
inlinenoexcept

◆ operator=() [1/2]

template<typename T>
Option& stx::Option< T >::operator= ( Option< T > &&  rhs)
inline

◆ operator=() [2/2]

template<typename T>
Option& stx::Option< T >::operator= ( Option< T > const &  rhs)
inline

◆ operator==() [1/3]

template<typename T>
template<typename U >
constexpr bool stx::Option< T >::operator== ( Option< U > const &  cmp) const
inline

◆ operator==() [2/3]

template<typename T>
template<typename U >
constexpr bool stx::Option< T >::operator== ( Some< U > const &  cmp) const
inline

◆ operator==() [3/3]

template<typename T>
constexpr bool stx::Option< T >::operator== ( NoneType const &  ) const
inlinenoexcept

◆ OR()

template<typename T>
constexpr auto stx::Option< T >::OR ( Option< T > &&  alt) && -> Option
inline

Returns the option if it contains a value, otherwise returns alt.

Arguments passed to OR are eagerly evaluated; if you are passing the result of a function call, it is recommended to use or_else, which is lazily evaluated.

Examples

Basic usage:

Option a = Some(2);
Option<int> b = None;
ASSERT_EQ(move(a).OR(move(b)), Some(2));
Option<int> c = None;
Option d = Some(100);
ASSERT_EQ(move(c).OR(move(d)), Some(100));
Option e = Some(2);
Option f = Some(100);
ASSERT_EQ(move(e).OR(move(f)), Some(2));
Option<int> g = None;
Option<int> h = None;
ASSERT_EQ(move(g).OR(move(h)), None);

◆ or_else()

template<typename T>
template<typename Fn >
constexpr auto stx::Option< T >::or_else ( Fn &&  op) && -> Option
inline

Returns the option if it contains a value, otherwise calls f and returns the result.

Examples

Basic usage:

auto nobody = []() -> Option<string> { return None; };
auto vikings = []() -> Option<string> { return Some("vikings"s); };
ASSERT_EQ(Option(Some("barbarians"s)).or_else(vikings),
Some("barbarians"s));
ASSERT_EQ(make_none<string>().or_else(vikings), Some("vikings"s));
ASSERT_EQ(make_none<string>().or_else(nobody), None);

◆ replace() [1/2]

template<typename T>
auto stx::Option< T >::replace ( T &&  replacement) -> Option
inline

Replaces the actual value in the option by the value given in parameter, returning the old value if present, leaving a Some in its place without deinitializing either one.

Examples

Basic usage:

Option x = Some(2);
auto old_x = x.replace(5);
ASSERT_EQ(x, Some(5));
ASSERT_EQ(old_x, Some(2));
Option<int> y = None;
auto old_y = y.replace(3);
ASSERT_EQ(y, Some(3));
ASSERT_EQ(old_y, None);

◆ replace() [2/2]

template<typename T>
auto stx::Option< T >::replace ( T const &  replacement) -> Option
inline

Replaces the actual value in the option by the value given in parameter, returning the old value if present, leaving a Some in its place without deinitializing either one.

Examples

Basic usage:

Option x = Some(2);
auto old_x = x.replace(5);
ASSERT_EQ(x, Some(5));
ASSERT_EQ(old_x, Some(2));
Option<int> y = None;
auto old_y = y.replace(3);
ASSERT_EQ(y, Some(3));
ASSERT_EQ(old_y, None);

◆ take()

template<typename T>
constexpr auto stx::Option< T >::take ( ) -> Option
inline

Takes the value out of the option, leaving a None in its place.

Examples

Basic usage:

Option a = Some(2);
auto b = a.take();
ASSERT_EQ(a, None);
ASSERT_EQ(b, Some(2));
Option<int> c = None;
auto d = c.take();
ASSERT_EQ(c, None);
ASSERT_EQ(d, None);

◆ unwrap()

template<typename T>
auto stx::Option< T >::unwrap ( ) && -> T
inline

Moves the value out of the Option<T> if it is in the variant state of Some<T>.

In general, because this function may panic, its use is discouraged. Instead, prefer to use pattern matching and handle the None case explicitly.

Panics

Panics if its value equals None.

Examples

Basic usage:

Option x = Some("air"s);
ASSERT_EQ(move(x).unwrap(), "air");
Option<string> y = None;
ASSERT_DEATH(move(y).unwrap());

◆ unwrap_none()

template<typename T>
void stx::Option< T >::unwrap_none ( ) &&
inline

Unwraps an option, expecting None and returning nothing.

Panics

Panics if the value is a Some.

Examples

Basic usage:

auto divide = [](double num, double denom) -> Option<double> {
if (denom == 0.0) return None;
return Some(num / denom);
};
ASSERT_DEATH(divide(0.0, 1.0).unwrap_none());
ASSERT_NO_THROW(divide(1.0, 0.0).unwrap_none());

◆ unwrap_or()

template<typename T>
constexpr auto stx::Option< T >::unwrap_or ( T &&  alt) && -> T
inline

Returns the contained value or an alternative: alt.

Arguments passed to unwrap_or are eagerly evaluated; if you are passing the result of a function call, it is recommended to use unwrap_or_else, which is lazily evaluated.

Examples

Basic usage:

ASSERT_EQ(Option(Some("car"s)).unwrap_or("bike"), "car");
ASSERT_EQ(make_none<string>().unwrap_or("bike"), "bike");

◆ unwrap_or_default()

template<typename T>
constexpr auto stx::Option< T >::unwrap_or_default ( ) && -> T
inline

Returns the contained value or a default of T

Consumes this object and returns its Some<T> value if it is a Some<T> variant, else if this object is a None variant, returns the default of the value type T.

Examples

Basic usage:

Option x = Some("Ten"s);
Option<string> y = None;
ASSERT_EQ(move(x).unwrap_or_default(), "Ten"s);
ASSERT_EQ(move(y).unwrap_or_default(), ""s);

◆ unwrap_or_else()

template<typename T>
template<typename Fn >
constexpr auto stx::Option< T >::unwrap_or_else ( Fn &&  op) && -> T
inline

Returns the contained value or computes it from a function.

Examples

Basic usage:

int k = 10;
auto alt = [&k]() { return 2 * k; };
ASSERT_EQ(make_some(4).unwrap_or_else(alt), 4);
ASSERT_EQ(make_none<int>().unwrap_or_else(alt), 20);

◆ value() [1/4]

template<typename T>
T& stx::Option< T >::value ( ) &
inlinenoexcept

Returns an l-value reference to the contained value. Note that no copying occurs here.

Panics

Panics if the value is a None

Examples

Basic usage:

auto x = make_some(9);
int& y = x.value();
y = 2;
ASSERT_EQ(x, Some(2));

◆ value() [2/4]

template<typename T>
T const& stx::Option< T >::value ( ) const &
inlinenoexcept

Returns a const l-value reference to the contained value. Note that no copying occurs here.

Panics

Panics if the value is a None

Examples

Basic usage:

auto const x = make_some(9);
int const& y = x.value();
ASSERT_EQ(y, 9);

◆ value() [3/4]

template<typename T>
T stx::Option< T >::value ( ) &&
delete

Use unwrap() instead.

◆ value() [4/4]

template<typename T>
T const stx::Option< T >::value ( ) const &&
delete

Use unwrap() instead.

◆ XOR()

template<typename T>
constexpr auto stx::Option< T >::XOR ( Option< T > &&  alt) && -> Option
inline

Returns whichever one of this object or alt is a Some<T> variant, otherwise returns None if neither or both are a Some<T> variant.

Examples

Basic usage:

Option a = Some(2);
Option<int> b = None;
ASSERT_EQ(move(a).XOR(move(b)), Some(2));
Option<int> c = None;
Option d = Some(2);
ASSERT_EQ(move(c).XOR(move(d)), Some(2));
Option e = Some(2);
Option f = Some(2);
ASSERT_EQ(move(e).XOR(move(f)), None);
Option<int> g = None;
Option<int> h = None;
ASSERT_EQ(move(g).XOR(move(h)), None);

Friends And Related Function Documentation

◆ internal::option::unsafe_value_move

template<typename T>
template<typename Tp >
Tp&& internal::option::unsafe_value_move ( Option< Tp > &  )
friend

Member Data Documentation

◆ storage_value_

template<typename T>
T stx::Option< T >::storage_value_

The documentation for this struct was generated from the following file:
Inheritance diagram for stx::Option< T >:
Inheritance graph
[legend]