std::stop_callback - cppreference.com
De cppreference.com
| Definido en el archivo de encabezado |
||
|
|
(desde C++20) | |
La plantilla de clase stop_callback proporciona un tipo objeto RAII con una función de devolución de llamada para un objeto std::stop_token asociado, de modo que la función de devolución de llamada se invocará cuando al objeto std::stop_source asociado con el std::stop_token se le solicite que se detenga.
Las funciones de devolución de llamada registradas mediante el constructor de stop_callback se invocan ya sea en el mismo hilo/subproceso que exitosamente invoque a request_stop() para un std::stop_source del std::stop_token asociado con el objeto stop_callback; o si ya se ha solicitado una detención anteriormente al registro del constructor, entonces la devolución de llamada se invoca en el hilo/subproceso que construye al objeto stop_callback.
Se puede crear más de un objeto stop_callback para el mismo std::stop_token, a partir del mismo hilo/subproceso o de distintos hilos simultáneos. No se da una garantía del orden en el que se ejecutarán, pero se invocarán sincrónicamente, excepto para los objetos stop_callback construidos después de que se ha solicitado la detención para el std::stop_token, como se describió previamente.
Si una invocación de una devolución de llamada egresa mediante una excepción, entoces se llama a std::terminate.
std::stop_callback no es ni CopyConstructible, CopyAssignable, MoveConstructible, ni MoveAssignable.
El tipo del parámetro de plantilla Callback debe ser tanto invocable como destructible. Cualquier valor de retorno se ignora.
Tipos miembro
| Tipo | Definición |
callback_type
|
Callback
|
Funciones miembro
| Construye un nuevo objeto stop_callback (función miembro pública) [editar] | |
| Destruye el objeto stop_callback (función miembro pública) [editar] | |
stop_callback no es asignable (función miembro pública) [editar] |
Guías de deducción
Ejemplo
#include <chrono> #include <condition_variable> #include <iostream> #include <mutex> #include <sstream> #include <thread> using namespace std::chrono_literals; // Uso de clase auxiliar para flujo atómico de std::cout class Writer { std::ostringstream buffer; public: ~Writer() { std::cout << buffer.str(); } Writer& operator<<(auto input) { buffer << input; return *this; } }; int main() { // Un hilo obrero // Esperará hasta que se solicite que se detenga. std::jthread worker([] (std::stop_token stoken) { Writer() << "id del hilo obrero: " << std::this_thread::get_id() << '\n'; std::mutex mutex; std::unique_lock lock(mutex); std::condition_variable_any().wait(lock, stoken, [&stoken] { return stoken.stop_requested(); }); }); // Registrar una devolución de llamada de detención en el hilo obrero. std::stop_callback callback(worker.get_stop_token(), [] { Writer() << "Devolución de llamada de detención ejecutada por el hilo: " << std::this_thread::get_id() << '\n'; }); // los objetos stop_callback objects pueden destruirse prematuramente // para prevenir su ejecución { std::stop_callback scoped_callback(worker.get_stop_token(), [] { // Esto no se ejecutará. Writer() << "Devolución de llamada de detención con ámbito ejecutada por el hilo: " << std::this_thread::get_id() << '\n'; }); } // Demostrar cuál hilo ejecuta a stop_callback cuándo. // Definir una función de detención auto stopper_func = [&worker] { if(worker.request_stop()) Writer() << "Solicitud de detención ejecutada por el hilo: " << std::this_thread::get_id() << '\n'; else Writer() << "Solicitud de detención no ejecutada por el hilo: " << std::this_thread::get_id() << '\n'; }; // Dejemos que múltiples hilos compitan por detener al hilo obrero std::jthread stopper1(stopper_func); std::jthread stopper2(stopper_func); stopper1.join(); stopper2.join(); // Después de que se ha solicitado una detención, // una nueva stop_callback se ejecuta inmediatemente. Writer() << "Hilo principal: " << std::this_thread::get_id() << '\n'; std::stop_callback callback_after_stop(worker.get_stop_token(), [] { Writer() << "Devolución de llamada de detención ejecutada por el hilo: " << std::this_thread::get_id() << '\n'; }); }
Posible salida:
id del hilo obrero: 140460265039616 Devolución de llamada de detención ejecutada por el hilo: 140460256646912 Solicitud de detención ejecutada por el hilo: 140460256646912 Solicitud de detención no ejecutada por el hilo: 140460248254208 Hilo principal: 140460265043776 Devolución de llamada de detención ejecutada por el hilo: 140460265043776