Namespaces
Variants

std:: move_if_noexcept

From cppreference.net
Utilities library
Definido en el encabezado <utility>
template < class T >
/* ver más abajo */ move_if_noexcept ( T & x ) noexcept ;
(desde C++11)
(constexpr desde C++14)

std::move_if_noexcept obtiene una referencia de valor derecho a su argumento si su constructor de movimiento no lanza excepciones o si no hay constructor de copia (tipo solo de movimiento), de lo contrario obtiene una referencia de valor izquierdo a su argumento. Normalmente se utiliza para combinar semántica de movimiento con garantía de excepción fuerte.

El tipo de retorno de std::move_if_noexcept es:

Contenidos

Parámetros

x - el objeto a ser movido o copiado

Valor de retorno

std :: move ( x ) o x , dependiendo de las garantías de excepción.

Complejidad

Constante.

Notas

Esto se utiliza, por ejemplo, por std::vector::resize , que puede tener que asignar nuevo almacenamiento y luego mover o copiar elementos del almacenamiento antiguo al nuevo. Si ocurre una excepción durante esta operación, std::vector::resize deshace todo lo que hizo hasta este punto, lo cual solo es posible si se utilizó std::move_if_noexcept para decidir si usar construcción por movimiento o construcción por copia (a menos que el constructor de copia no esté disponible, en cuyo caso se usa el constructor de movimiento de todas formas y la garantía fuerte de excepción puede ser suspendida).

Ejemplo

#include <iostream>
#include <utility>
struct Bad
{
    Bad() {}
    Bad(Bad&&) // puede lanzar excepción
    {
        std::cout << "Throwing move constructor called\n";
    }
    Bad(const Bad&) // también puede lanzar excepción
    {
        std::cout << "Throwing copy constructor called\n";
    }
};
struct Good
{
    Good() {}
    Good(Good&&) noexcept // NO lanzará excepción
    {
        std::cout << "Non-throwing move constructor called\n";
    }
    Good(const Good&) noexcept // NO lanzará excepción
    {
        std::cout << "Non-throwing copy constructor called\n";
    }
};
int main()
{
    Good g;
    Bad b;
    [[maybe_unused]] Good g2 = std::move_if_noexcept(g);
    [[maybe_unused]] Bad b2 = std::move_if_noexcept(b);
}

Salida:

Non-throwing move constructor called
Throwing copy constructor called

Véase también

(C++11)
reenvía un argumento de función y utiliza el argumento de plantilla de tipo para preservar su categoría de valor
(plantilla de función)
(C++11)
convierte el argumento a un xvalue
(plantilla de función)