cpp / latest / utility / optional / and_then.html /

std::optional<T>::and_then

template< class F >
constexpr auto and_then( F&& f ) &;
(1) (since C++23)
template< class F >
constexpr auto and_then( F&& f ) const&;
(2) (since C++23)
template< class F >
constexpr auto and_then( F&& f ) &&;
(3) (since C++23)
template< class F >
constexpr auto and_then( F&& f ) const&&;
(4) (since C++23)

Returns the result of invocation of f on the contained value if it exists. Otherwise, returns an empty value of the return type.

The return type (see below) must be a specialization of std::optional. Otherwise, the program is ill-formed.

1) Equivalent to
if (*this)

return std::invoke(std::forward<F>(f), this->value());
else
.

return std::remove_cvref_t<std::invoke_result_t<F, T&>>();
.
2) Equivalent to
if (*this)

return std::invoke(std::forward<F>(f), this->value());
else
.

return std::remove_cvref_t<std::invoke_result_t<F, const T&>>();
.
3) Equivalent to
if (*this)

return std::invoke(std::forward<F>(f), std::move(this->value()));
else
.

return std::remove_cvref_t<std::invoke_result_t<F, T>>();
.
4) Equivalent to
if (*this)

return std::invoke(std::forward<F>(f), std::move(this->value()));
else
.

return std::remove_cvref_t<std::invoke_result_t<F, const T>>();
.

Parameters

f - a suitable function or Callable object that returns an std::optional

Return value

The result of f or an empty std::optional, as described above.

Notes

Some languages call this operation flatmap.

Feature testing macro: __cpp_lib_monadic_optional.

Example

#include <optional>
#include <vector>
#include <iostream>
#include <string>
#include <charconv>
#include <ranges>
std::optional<int> to_int(std::string_view sv)
{
  int r{};
  auto [ptr, ec] { std::from_chars(sv.data(), sv.data() + sv.size(), r) };
  if (ec == std::errc()) 
    return r;
  else
    return std::nullopt;
}
 
int main()
{
    using namespace std::literals;
 
    std::vector<std::optional<std::string>> v = {
     "1234", "15 foo", "bar", "42", "5000000000", " 5"
    };
 
    for( auto&& x : v | std::views::transform([](auto&& o) { return
          o.and_then(to_int)                     // flatmap from strings to ints
                                                 // (making empty optionals where it fails)
           .transform([](int n) { return n+1; })               // map int to int + 1
           .transform([](int n) { return std::to_string(n); }) // convert back to strings
           .or_else([]{ return std::optional{"Null"s}; // replace all empty optionals
                                                       // that were left by and_then and
                                                       // ignored by transforms with "Null"
        }); }) )
      std::cout << *x << '\n';
}

Output:

1235
16
Null
43
Null
Null

See also

returns the contained value if available, another value otherwise
(public member function)
(C++23)
returns an optional containing the transformed contained value if it exists, or an empty optional otherwise
(public member function)
(C++23)
returns the optional itself if it contains a value, or the result of the given function otherwise
(public member function)

© cppreference.com
Licensed under the Creative Commons Attribution-ShareAlike Unported License v3.0.
https://en.cppreference.com/w/cpp/utility/optional/and_then