Biblioteca estándar de C++<future>

C++11 introdujo<future>el archivo de encabezado, que proporciona un mecanismo de programación asíncrona, permitiendo que el programa continúe ejecutando otras tareas mientras espera que se complete una operación.<future>La biblioteca es parte de la programación concurrente en la biblioteca estándar de C++, y permite a los programadores manejar operaciones asíncronas de una manera más concisa y segura.

<future>En la biblioteca se definen varios tipos clave:

  • std::future: representa el resultado de una operación asíncrona; se puede consultar el estado de la operación, obtener el resultado o esperar a que la operación se complete.
  • std::promise: se utiliza parastd::futureemparejar y establecer el resultado de la operación asíncrona.
  • std::packaged_task: encapsula una función u objeto invocable, permitiendo que se ejecute como una tarea asíncrona.

std::promise

std::promiseSe utiliza para establecer el resultado de una operación asíncrona. Se usastd::futureen pareja.

Ejemplo

#include <iostream>
#include <future>

int main() {
    std::promise<int> prom;
    std::future<int> fut = prom.get_future();

    // Establecer el resultado en otro hilo
    std::thread t([prom]() {
        prom.set_value(10);
    });

    // Esperar el resultado
    std::cout << "Future value: " << fut.get() << std::endl;

    t.join();
    return 0;
}

Salida:

Future value: 10

std::packaged_task

std::packaged_taskEncapsula una función u objeto invocable para que pueda ejecutarse como una tarea asíncrona.

Ejemplo

#include <iostream>
#include <future>
#include <cmath>

int compute_square_root(double x) {
    return std::sqrt(x);
}

int main() {
    std::packaged_task<double(double)> task(compute_square_root);
    std::future<double> result = task.get_future();
    std::thread th(std::move(task), 9.0);

    std::cout << "Result: " << result.get() << std::endl;
    th.join();
    return 0;
}

Salida:

Result: 3

std::async

std::asynces una función conveniente para iniciar tareas asíncronas. Puede devolver inmediatamente unstd::futureobjeto.

Ejemplo

#include <iostream>
#include <future>

int main() {
    std::future<int> fut = std::async(std::launch::async, [](int x) {
        return x * x;
    }, 5);

    std::cout << "Result: " << fut.get() << std::endl;
    return 0;
}

Salida:

Result: 25

Manejo de excepciones

Cuando una operación asíncrona lanza una excepción,std::futurecaptura esta excepción, y se puede, mediante la llamada al.get()método, volver a lanzarla.

Ejemplo

#include <iostream>
#include <future>

void throw_exception() {
    throw std::runtime_error("Exception thrown");
}

int main() {
    std::future<void> fut = std::async(throw_exception);

    try {
        fut.get();
    } catch (const std::exception& e) {
        std::cout << "Caught exception: " << e.what() << std::endl;
    }
    return 0;
}

Salida:

Caught exception: Exception thrown

<future>La biblioteca proporciona a los programadores de C++ una forma sencilla y potente de programación asíncrona. Al utilizarlastd::promise、std::packaged_taskystd::async, podemos implementar fácilmente operaciones concurrentes y asíncronas en programas de C++.

Otras extensiones