template <typename F> 
auto recover(F&& f) const&
(1)
template <typename E, typename F> 
auto recover(E&& e, F&& f) const&
(2)
template <typename F>
auto recover(F&& f) &&
(3)
template <typename E, typename F>
auto recover(E&& e, F&& f) &&
(4)

Since the futures are value based, the recover method should be used to do the error handling.

  1. Constructs a recoverable continuation that gets a future<T> passed. It uses the same executor as this.

  2. Constructs a recoverable continuation that gets a future<T> passed. It uses the provided executor.

  3. Constructs a recoverable continuation on an r-value future. It gets a future<T> passed. It uses the same executor as this.

  4. Constructs a recoverable continuation on an r-value future. It gets a future<T> passed. It uses the the provided executor.

Parameters

e

Executor which is used to schedule the resulting task

f

Callable object that implements the recover() function. Its parameter must be of type of this future<T> instance.

It returns the recoverable future

Example 1

#include <iostream>
#include <stdexcept>
#include <thread>
#include <stlab/concurrency/default_executor.hpp>
#include <stlab/concurrency/future.hpp>

using namespace std;
using namespace stlab;

int main() {
    auto x = async(default_executor, [] { 
      throw runtime_error("Vogons did arrive!"); 
      return 42; 
    });

    auto r = x.recover([](future<int> f) { 
        try {
          auto answer = f.get_try().value();
          cout << "The answer is " << answer << '\n';
        }
        catch (const exception& ex) {
          cout << "The error \"" << ex.what() << "\" happened!\n";
        }
      });

    // Waiting just for illustrational purpose
    while (!r.get_try()) { this_thread::sleep_for(chrono::milliseconds(1)); }
}

// Result: The error "Vogons did arrive!" happened!