es.davy.ai

Preguntas y respuestas de programación confiables

¿Tienes una pregunta?

Si tienes alguna pregunta, puedes hacerla a continuación o ingresar lo que estás buscando.

¿Por qué no se llama al constructor de movimiento?

Tengo el siguiente fragmento de código:

“`c++

#include <iostream>

struct T {
int a;

<pre><code>T() = default;

T(T& other) {
std::cout << "copy &\n";
}

T(T&& other) {
std::cout << "move &&\n";
}
</code></pre>

};

void foo(T&& x) {
T y(x); // ¿Por qué se llama al constructor de copia?
}

int main() {
T x;
foo(std::move(x));

<pre><code>return 0;
</code></pre>

}

“`

No entiendo por qué se prefiere el constructor de copia en lugar del constructor de movimiento, a pesar de que foo() acepta una referencia de valor de rvalue.

Tags:  , , ,

Answer

  1. Avatar for davy.ai

    La razón por la cual se llama al constructor de copia en este código es que el parámetro pasado a foo() es una expresión lvalue (x). Aunque foo() acepta una referencia de valor temporal (rvalue-reference), una lvalue también puede unirse a ella.

    En este caso, cuando std::move(x) se pasa como argumento a foo(), simplemente convierte x en una expresión de valor temporal (rvalue) y la pasa a la función. Dentro de foo(), la expresión T y(x) crea un objeto nuevo y y lo inicializa usando el constructor de copia, ya que x es una referencia lvalue a T.

    Para forzar que se llame al constructor de movimiento en su lugar, debe cambiar la firma de foo() para tomar una referencia lvalue (T& x), o convertir x a una referencia de valor temporal dentro de foo() utilizando std::move():

    c++
    void foo(T&& x) {
    T y(std::move(x)); // se llama al constructor de movimiento
    }

Comments are closed.